I need to make a menu that list the .txt files in a directory. For example, if i have jonsmith12.txt , lenovo123.txt , dell123.txt in the directory how would I make an arraylist menu of:
Please choose one of the following:
jonsmith12
lenovo123
dell123
Please enter your choice:
I need an arraylist menu is because I don't know how many .txt files are in the directory at any given time.
import java.io.File;
public class ListFiles
{
public static void listRecord() {
// Directory path here
String path = ".";
String files;
File folder = new File(path);
File[] listOfFiles = folder.listFiles();
for (int i = 0; i < listOfFiles.length; i++)
{
if (listOfFiles[i].isFile())
{
files = listOfFiles[i].getName();
if (files.endsWith(".txt") || files.endsWith(".TXT"))
{
System.out.println(files);
}
}
}
}
}
Here is the class that will display the information in the .txt file onto the console. It stills need some modifying too but I could probably figure that out.
import java.io.BufferedInputStream;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
/**
* This program reads a text file line by line and print to the console. It uses
* FileOutputStream to read the file.
*
*/
public class DisplayRec {
public static void displayRecord() throws IOException {
File file = new File("williamguo5.txt");
FileInputStream fis = null;
BufferedInputStream bis = null;
DataInputStream dis = null;
try {
fis = new FileInputStream(file);
// Here BufferedInputStream is added for fast reading.
bis = new BufferedInputStream(fis);
dis = new DataInputStream(bis);
// dis.available() returns 0 if the file does not have more lines.
while (dis.available() != 0) {
// this statement reads the line from the file and print it to
// the console.
System.out.println(dis.readLine());
}
// dispose all the resources after using them.
fis.close();
bis.close();
dis.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
So the question is: How do I implement a ArrayList menu into my ListFiles class so it will display the .txt files.
You can use the alternate method signature for File.listFiles(FilenameFilter filter) to simplify your code:
File[] files = dir.listFiles(new FilenameFilter() {
#Override
public boolean accept(File dir, String name) {
return name.toLowerCase().endsWith(".txt");
}
});
And unless you really enjoy writing loops, you don't even need to manually loop over the array to convert it to a List:
List<File> lstRecords = Arrays.asList(files);
Your displayRecord method was pretty close; you just needed to pass the file as an argument and use that instead of a hard-coded filename, and you needed to initialize dis.
Putting it all together:
package com.example.file;
import java.io.BufferedInputStream;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FilenameFilter;
import java.io.IOException;
import java.util.Arrays;
import java.util.List;
public class FileExample {
public static List<File> listRecords(File dir) {
File[] files = dir.listFiles(new FilenameFilter() {
#Override
public boolean accept(File dir, String name) {
return name.toLowerCase().endsWith(".txt");
}
});
return Arrays.asList(files);
}
public static void displayRecord(File file) {
FileInputStream fis = null;
BufferedInputStream bis = null;
DataInputStream dis = null;
try {
fis = new FileInputStream(file);
// Here BufferedInputStream is added for fast reading.
bis = new BufferedInputStream(fis);
dis = new DataInputStream(bis);
String line = dis.readLine();
while (line != null) {
// this statement reads the line from the file and print it to
// the console.
System.out.println(line);
line = dis.readLine();
}
// dispose all the resources after using them.
fis.close();
bis.close();
dis.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
/**
* #param args
*/
public static void main(String[] args) {
List<File> lstRecords = listRecords(new File("."));
for (File record : lstRecords) {
displayRecord(record);
}
}
}
It's also better to use Reader/Writer instead of InputStream/OutputStream if you're working with text files, and you should close your files in the finally block to avoid a potential resource leak.
You'll also notice I didn't explicitly use an ArrayList. In most cases, it's better to program against the interface (in this case, List) as much as possible, and only declare variables using the implementing class when you need to use a method that's only available to that class.
It looks like your sticking point above is the array. If you just need to iterate over the files in a directory, something as simple as the following will do the trick.
import java.io.File;
public class TxtEnumerator {
public static void main(String[] args) {
TxtEnumerator te = new TxtEnumerator();
te.listFiles();
}
public void listFiles() {
String filepath = "." + File.separator + "textDirectory";
File file = new File(filepath);
if (file.isDirectory()) {
for (File f : file.listFiles()) {
if (f.getName().endsWith(".txt")) {
System.out.println(f.getName());
}
}
}
}
}
Related
I have a piece of code that iterates over all the files in a directory.
But I am stuck now at reading the content of the file into a String object.
public String filemethod(){
if (path.isDirectory()) {
files = path.list();
String[] ss;
for (int i = 0; i < files.length; i++) {
ss = files[i].split("\\.");
if (files[i].endsWith("txt"))
System.out.println(files[i]);
}
}
return String.valueOf(files);
}
Faced with a similar problem and wrote a code a while back. This will read the content of all files of a directory.
May require adjustments based on your file directories but its tried and tested code.Hope this helps :)
package FileHandling;
import java.io.*;
import java.util.ArrayList;
import java.util.Collections;
public class BufferedInputStreamExample {
FileInputStream fis = null;
BufferedInputStream bis = null;
DataInputStream dis = null;
public void readFile(File folder) {
ArrayList<File> myFiles = listFilesForFolder(folder);
for (File f : myFiles) {
String path = f.getAbsolutePath();
//Path of the file(Optional-You can know which file's content is being printed)
System.out.println(path);
File infile = new File(path);
try {
fis = new FileInputStream(infile);
bis = new BufferedInputStream(fis);
dis = new DataInputStream(bis);
while (dis.available() != 0) {
String line = dis.readLine();
System.out.println(line);
}
} catch (IOException e) {
} finally {
try {
fis.close();
bis.close();
dis.close();
} catch (Exception ex) {
}
}
}
}
public ArrayList<File> listFilesForFolder(final File folder){
ArrayList<File> myFiles = new ArrayList<File>();
for (File fileEntry : folder.listFiles()) {
if (fileEntry.isDirectory()) {
myFiles.addAll(listFilesForFolder(fileEntry));
} else {
myFiles.add(fileEntry);
}
}
return myFiles;
}
}
Main method
package FileHandling;
import java.io.File;
public class Main {
public static void main(String args[]) {
//Your directory here
final File folder = new File("C:\\Users\\IB\\Documents\\NetBeansProjects\\JavaIO\\files");
BufferedInputStreamExample bse = new BufferedInputStreamExample();
bse.readFile(folder);
}
}
I would use following code:
public static Collection<File> allFilesInDirectory(File root) {
Set<File> retval = new HashSet<>();
Stack<File> todo = new Stack<>();
todo.push(root);
while (!todo.isEmpty()) {
File tmp = todo.pop();
if (tmp.isDirectory()) {
for (File child : tmp.listFiles())
todo.push(child);
} else {
if (isRelevantFile(tmp))
retval.add(tmp);
}
}
return retval;
}
All you need then is a method that defines what files are relevant for your usecase (for instance txt)
public static boolean isRelevantFile(File tmp) {
// get the extension
String ext = tmp.getName().contains(".") ? tmp.getName().substring(tmp.getName().lastIndexOf('.') + 1) : "";
return ext.equalsIgnoreCase("txt");
}
Once you have all the files, you can easily get all the text with a little hack in Scanner
public static String allText(File f){
// \\z is a virtual delimiter that marks end of file/string
return new Scanner(f).useDelimiter("\\z").next();
}
So now, using these methods you can easily extract all the text from an entire directory.
public static void main(String[] args){
File rootDir = new File(System.getProperty("user.home"));
String tmp = "";
for(File f : allFilesInDirectory(rootDir)){
tmp += allText(f);
}
System.out.println(tmp);
}
import java.io.File;
import java.io.FilenameFilter;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
public class ReadDataFromFiles {
static final File DIRECTORY = new File("C:\\myDirectory");
public static void main(String[] args) throws IOException {
StringBuilder sb = new StringBuilder();
//append content of each file to sb
for(File f : getTextFiles(DIRECTORY)){
sb.append(readFile(f)).append("\n");
}
System.out.println(sb.toString());
}
// get all txt files from the directory
static File[] getTextFiles(File dir){
FilenameFilter textFilter = (File f, String name) -> name.toLowerCase().endsWith(".txt");
return dir.listFiles(textFilter);
}
// read the content of a file to string
static String readFile(File file) throws IOException{
return new String(Files.readAllBytes(Paths.get(file.getAbsolutePath())), StandardCharsets.UTF_8);
}
}
I have the following code seen below, this code looks through a directory and then prints all of the different file names. Now my question is, how would I go about changing my code, so that it would also print out all of the content within the files which it finds/prints? As an example, lets say the code finds 3 files in the directory, then it would print out all the content within those 3 files.
import java.io.File;
import java.io.IOException;
public class EScan {
static String usernamePc = System.getProperty("user.name");
final static File foldersPc = new File("/Users/" + usernamePc + "/Library/Mail/V2");
public static void main(String[] args) throws IOException {
listFilesForFolder(foldersPc);
}
public static void listFilesForFolder(final File foldersPc) throws IOException {
for (final File fileEntry : foldersPc.listFiles()) {
if (fileEntry.isDirectory()) {
listFilesForFolder(fileEntry);
} else {
System.out.println(fileEntry.getName());
}
}
}
}
I tested it before posting. it is working.
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.logging.Level;
import java.util.logging.Logger;
/**
* #author EdwinAdeola
*/
public class TestPrintAllFiles {
public static void main(String[] args) {
//Accessing the folder path
File myFolder = new File("C:\\Intel");
File[] listOfFiles = myFolder.listFiles();
String fileName, line = null;
BufferedReader br;
//For each loop to print the content of each file
for (File eachFile : listOfFiles) {
if (eachFile.isFile()) {
try {
//System.out.println(eachFile.getName());
fileName = eachFile.getAbsolutePath();
br = new BufferedReader(new FileReader(fileName));
try {
while ((line = br.readLine()) != null) {
System.out.println(line);
}
} catch (IOException ex) {
Logger.getLogger(TestPrintAllFiles.class.getName()).log(Level.SEVERE, null, ex);
}
} catch (FileNotFoundException ex) {
Logger.getLogger(TestPrintAllFiles.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
}
}
You may use Scanner to read the contents of the file
try {
Scanner sc = new Scanner(fileEntry);
while (sc.hasNextLine()) {
String s = sc.nextLine();
System.out.println(s);
}
sc.close();
} catch (Exception e) {
e.printStackTrace();
}
You can try one more way if you find suitable :
package com.grs.stackOverFlow.pack10;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.util.Arrays;
import java.util.List;
public class EScan {
public static void main(String[] args) throws IOException {
File dir=new File("C:/your drive/");
List<File> files = Arrays.asList(dir.listFiles(f->f.isFile()));
//if you want you can filter files like f->f.getName().endsWtih(".csv")
for(File f: files){
List<String> lines = Files.readAllLines(f.toPath(),Charset.defaultCharset());
//processing line
lines.forEach(System.out::println);
}
}
}
Above code can me exploited in number of ways like processing line can be modified to add quotes around lines as below:
lines.stream().map(t-> "'" + t+"'").forEach(System.out::println);
Or print only error messages lines
lines.stream().filter(l->l.contains("error")).forEach(System.out::println);
Above codes and variations are tested.
I am currently practicing with splitting and merging a file. I found a piece of code on the web authored by a "krishna" with split and merge classes. The splitter worked like a charm, and I did some modifications to make it work the way I like it.
Here's the catch: I want the merger class to open the .00x files the splitter generates. But it is only limited to exactly eight .00x files, no more no less.
If only I could make it read all .00x files in the folder. I've been thinking long for a solution but I can't seem to generate one. I thought about making something that will scan the number of file with the .00x extension and make a loop based on it. Pls help me, or at least give me hints. Thank you! The code follows:
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.util.ArrayList;
import java.util.List;
import javax.swing.JOptionPane;
public class MergeFile {
private static String FILE_NAME = JOptionPane.showInputDialog("Enter the file name");
public static void main(String[] args) {
File ofile = new File(FILE_NAME);
FileOutputStream fos;
FileInputStream fis;
short[] fileBytes;
int bytesRead = 0;
List<File> list = new ArrayList<File>();
list.add(new File(FILE_NAME+".001"));
list.add(new File(FILE_NAME+".002"));
list.add(new File(FILE_NAME+".003"));
list.add(new File(FILE_NAME+".004"));
list.add(new File(FILE_NAME+".005"));
list.add(new File(FILE_NAME+".006"));
list.add(new File(FILE_NAME+".007"));
list.add(new File(FILE_NAME+".008"));
try {
fos = new FileOutputStream(ofile,true);
for (File file : list) {
fis = new FileInputStream(file);
fileBytes = new byte[(int) file.length()];
bytesRead = fis.read(fileBytes, 0,(int) file.length());
assert(bytesRead == fileBytes.length);
assert(bytesRead == (int) file.length());
fos.write(fileBytes);
fos.flush();
fileBytes = null;
fis.close();
fis = null;
}
fos.close();
fos = null;
}catch (Exception exception){
exception.printStackTrace();
}
}
}
You can implement a FileFilter and pass it to the method File.listFiles() as shown below:
import java.io.File;
import java.io.FileFilter;
import java.util.Arrays;
import java.util.List;
public class Test {
public static void main(String[] args) {
final String FILE_NAME = "testfile";
/* The method listFiles returns all the files in the path
(I used "." to select the working directory).
This method accept a FileFilter as parameter. The file filter
decides what files to return. It is a simple interface with just
one method. */
File[] fileList = new File(".").listFiles(new FileFilter() {
#Override
public boolean accept(File pathname) {
/* Return true to include the file in the list */
return pathname.getName().startsWith(FILE_NAME);
}
});
List<File> list = Arrays.asList(fileList);
for (File f: list) {
System.out.println(f);
}
}
}
If you do not like to work with anonymous classes, you can just implement your FileFilter as a public class in its own file.
If you are using Java 8, then you can do it pretty easily using Files#list. Getting your list of Files starting with FILE_NAME and ending with .001, .002, .003, ... should work like this:
Path path = Paths.get(FILE_NAME);
Pattern pattern = Pattern.compile(Pattern.quote(path.getFileName().toString()) + "\\.\\d{3}");
List<File> list = Files.list(path.getParent())
.filter(f -> pattern.matcher(f.getFileName().toString()).matches())
.map(Path::toFile)
.collect(Collectors.toList());
This is just from the top of my head, I didn't test it as I had no .00x files lying around.
import java.io.File;
import java.io.FilenameFilter;
import java.util.Arrays;
import java.util.regex.Pattern;
public class ListFiles {
private static final String BASE_DIR = "<your directory>";
private static final String FILE_EXT = ".*\\.[0-9]{3,3}";
private class FileFilter implements FilenameFilter {
private String ext;
public FileFilter(String ext) {
this.ext = ext;
}
public boolean accept(File dir, String name) {
return Pattern.matches(ext, name) ? true : false;
}
}
public static void main(String args[]) {
System.out.println(Arrays.toString(new ListFiles().listFile(BASE_DIR, FILE_EXT)));
}
public String[] listFile(String folder, String ext) {
File dir = new File(folder);
String[] list = dir.list(new FileFilter(ext));
return list;
}
}
I am trying to create a file from a log report. To save the file I've created a button. When the button is pushed, the following code is executed:
public void SAVE_REPORT(KmaxWidget widget){//save
try {
String content = report.getProperty("TEXT");
File file = new File("logKMAX.txt");
// if file doesnt exists, then create it
if (!file.exists()) {
file.createNewFile();
}
FileWriter fw = new FileWriter(file.getAbsoluteFile());
BufferedWriter bw = new BufferedWriter(fw);
bw.write(content);
bw.close();
} catch (IOException e) {
e.printStackTrace();
}
} //SAVE_REPORT
I have no compilation errors, but there isn't any file saved.
Any idea on what might be wrong?
Use the new file API. For one, in your program, you don't verify the return value of .createNewFile(): it doesn't throw an exception on failure...
With the new file API, it is MUCH more simple:
public void saveReport(KmaxWidget widget)
throws IOException
{
final String content = report.getProperty("TEXT");
final Path path = Paths.get("logKMAX.txt");
try (
final BufferedWriter writer = Files.newBufferedWriter(path,
StandardCharsets.UTF_8, StandardOpenOption.CREATE);
) {
writer.write(content);
writer.flush();
}
}
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;
public class moveFolderAndFiles
{
public static void main(String[] args) throws Exception
{
File sourceFolder = new File("c:\\Audio Bible");
copyFolder(sourceFolder);
}
private static void copyFolder(File sourceFolder) throws Exception
{
File files[] = sourceFolder.listFiles();
int i = 0;
for (File file: files){
if(file.isDirectory()){
File filter[] = new File(file.getAbsolutePath()).listFiles();
for (File getIndividuals: filter){
System.out.println(i++ +"\t" +getIndividuals.getPath());
File des = new File("c:\\audio\\"+getIndividuals.getName());
Files.copy(getIndividuals.toPath(), des.toPath(), StandardCopyOption.REPLACE_EXISTING);
}
}
}
}
}
I'm writing a little program that just takes a file, and trims the last 4 characters after a space and writes those to a new file. When I tell it to do this and then print them to console it works fine. They show up fine and everything works. But when I use the BufferedWriter to write it to a new file it gives me a weird string of characters in that file when I check it. Here is my code:
package trimmer;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Scanner;
public class trimmer {
private File file;
private File newfile;
private Scanner in;
public void Create() {
String temp, temp1;
try {
setScanner(new Scanner(file));
} catch (FileNotFoundException e) {
System.out.println("file not found!!");
}
if (!newfile.exists()) {
try {
newfile.createNewFile();
FileWriter fw = new FileWriter(newfile.getAbsoluteFile());
BufferedWriter bw = new BufferedWriter(fw);
while (in.hasNextLine()) {
temp1 = in.nextLine();
temp = temp1.substring(temp1.lastIndexOf(' ') + 1);
System.out.println(temp);
bw.write(temp);
}
bw.close();
System.out.println("done!");
} catch (IOException e) {
System.out.println("Could not make new file: " + newfile + " Error code: " + e.getMessage());
}
}
}
public Scanner getScanner() {
return in;
}
public void setScanner(Scanner in) {
this.in = in;
}
public File getFile() {
return file;
}
public void setFile(File file) {
this.file = file;
}
public File getNewfile() {
return newfile;
}
public void setNewfile(File newfile) {
this.newfile = newfile;
}
}
and when I check the file it looks like this:
䐳噔吳商吳啍唳噎吳剄唳剄䘳剄唳噎吳商䠳卉䌳䕎䜳䱁䠳卉䴳㉕倳乓䐳䍐䐳啐吳䍖吳乓吳啍䔳䥘䌳噔匳剕唳乓唳䅍䌳䕎䜳䱁䴳㉕倳乓䐳䍐䐳啐吳䍖䠳卉吳乓吳啍䔳䥘䌳噔匳剕唳乓唳䅍
Can anyone tell me why this would be happening?
FileWriter uses the platform default character encoding. If this is not the encoding that you want, then you need to use an OutputStreamWriter with the appropriately chosen character encoding.