Get the name of a file given as input in cmd - java

I'm currently working on a project and i need some help. Depending on the user input I have to read some data off some txt files. There are three ways to call the program:
java Graph [-u] -s start example_graph.txt
java Graph [-u] -a example_graph.txt
java Graph [-u] -d traffic.txt
The files i have to read depending on what the user chose are :
clrs.txt, traffic.txt, traffic_u.txt, facebook_combined_u.txt
The method I'm using to read and store the data of the file is
public void readFile() {
String txtFile = "filename.csv";
BufferedReader br = null;
String line = "";
String txtSplitBy = ",";
try {
br = new BufferedReader(new FileReader(txtFile));
while ((line = br.readLine()) != null) {
String[] dj = line.split(txtSplitBy);
int node_a = Integer.parseInt(dj[0]);
int node_b = Integer.parseInt(dj[1]);
int weight = Integer.parseInt(dj[2]);
if (node_a > adj.size()) {
for (int i = adj.size() + 1; i <= node_a; i++) {
adj.add(new HashSet<Link>());
}
}
HashSet<Link> h = adj.get(node_a);
h.add(new Link(node_b, weight));
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (br != null) {
try {
br.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
But this method only works if I have a specific file as input. Now that there are more than one files how can I get the file name into a String?

As pointed out in the comments, you can read arguments from the cmd line in the args area of the main method, for example:
public class SO {
public static void main(String[] args) {
for(String s : args){ //For each argument
if(s.indexOf(".") != -1){ //If contains a dot (like a file ext)
System.out.println(s); //print
}
}
}
}
When running this with:
java SO [-u] -a example_graph.txt
It wrote out the name of the file.
Hope this helps!

Related

Read, and then split a text file into different arrays

So I'm trying to use a BufferedReader to split a text file into 2 different arrays, I've written some code but I'm not sure where to go from here.
I know how to populate an array, but i just cant seem to get the specific lines.
So, one array for NEW_OFFICE containing only the numbers, and one for MAIN_ADDRESS containing only the numbers below it.
BufferedReader in = null;
try {
in = new BufferedReader(new FileReader("myDelivery.txt"));
String read = null;
while ((read = in.readLine()) != null) {
String words = read.split("NEW_OFFICE")[0];
}
} catch (IOException e) {
System.out.println("There was a problem: " + e);
e.printStackTrace();
} finally {
try {
in.close();
} catch (Exception ignored) { }
}
This is the text file:
NEW_OFFICE
-92.48392883 52.96531732
-2.483984994 92.48392883
MAIN_ADDRESS
-1.207614869 52.98908196
NEW_OFFICE always is the first line, and always has two lines below
it, the same goes for MAIN_ADDRESS it always has one line below it.
NEW_OFFICE & MAIN_ADDRESS can't appear more than once.
Based on your comment mentioned above, given below is the solution:
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.Arrays;
public class Main {
public static void main(String[] args) throws IOException {
String[][] office = new String[2][2];
String[][] main = new String[1][2];
try (BufferedReader in = new BufferedReader(new FileReader("myDelivery.txt"))) {
String read;
while ((read = in.readLine()) != null) {
if (read.equalsIgnoreCase("NEW_OFFICE")) {
// Read next two lines
for (int i = 0; i < 2; i++) {
if ((read = in.readLine()) != null) {
office[i] = read.split("\\s+");
}
}
} else if (read.equalsIgnoreCase("MAIN_ADDRESS")) {
// Read next line
if ((read = in.readLine()) != null) {
main[0] = read.split("\\s+");
}
}
}
}
// Display office[][]
System.out.println("Displaying office:");
for (String[] officeData : office) {
System.out.println(Arrays.toString(officeData));
}
// Display main[][]
System.out.println("Displaying main:");
for (String[] mainData : main) {
System.out.println(Arrays.toString(mainData));
}
}
}
Output:
Displaying office:
[-92.48392883, 52.96531732]
[-2.483984994, 92.48392883]
Displaying main:
[-1.207614869, 52.98908196]
Notes:
\\s+ is for splitting the line on space(s).
Use try-with-resources syntax to simplify your code.
.split() does take a string, but it should be a regex, not the substring that you want to split it on. You want to change your code like this:
try (BufferedReader in = new BufferedReader(new FileReader("x.txt"))) {
String read;
String office = "";
while ((read = in.readLine()) != null) {
if (read.contains("NEW_OFFICE")) {
office = "NEW_OFFICE";
} else if (read.contains("MAIN_ADDRESS")) {
office = "MAIN_ADDRESS";
} else {
System.out.println(office + " : " + read);
}
}
} catch (IOException e) {
e.printStackTrace();
}
I have also changed your try with try-with-resources so you don't have to worry about closing the resource.
I´d go with somethin like this.
Please be aware that I don´t have an IDE right now so this is basically pseudo code:
try (BufferedReader in = new BufferedReader(new FileReader("x.txt"))) {
String line = null;
boolean isOffice = false;
ArrayList<double> officeInts = new ArrayList<double>();
ArrayList<double> addressInts = new ArrayList<double>();
while ((line = in.readLine()) != null) {
if (line.contains("NEW_OFFICE")) {
isOffice = true;
continue;
} else if (line.contains("MAIN_ADDRESS")) {
isOffice = false;
continue;
}
for(String s : line.split(" "){
double num = Double.parseDouble(s);
if(isOffice) {
officeInts.add(num);
} else {
addressInts.add(num);
}
}
}
} catch (IOException e) {
e.printStackTrace();
}

Why I could not save the contents of a file after reading it twice?

Already fixed. Thanks for Mas & ruhul for observing my bugs.
I was trying to read a text file twice, named stationary.txt. The contents of the file has three columns such as the amount, the name of product and the total price.
What I am trying to do first is by averaging each product's price by reading line by line. Then I closed the Buffered and then open it again and read. The second reading takes a variable average and compares each product's price line by line. If line 1 is over the average, then write it into dearer.txt, otherwise write it into cheap.txt
Here is the stationary.txt
1 Highlighter 5.99
2 Pen 9.00
3 Eraser 5.00
4 DrawingPin 2.75
5 Highlighter 10.99
6 FountainPen 20.50
7 Pencil 14.50
Below is the source code
import java.util.*;
import java.io.*;
public class Ques {
public static void main(String[] args) throws FileNotFoundException {
double average = 0;
File inFile = new File("stationary.txt");
FileReader fileReader = new FileReader(inFile);
BufferedReader bufReader = new BufferedReader(fileReader);
File outFilel = new File("dearer.txt");
FileOutputStream outFileStreaml = new FileOutputStream(outFilel);
PrintWriter outStream1 = new PrintWriter(outFileStreaml);
File outFile2 = new File("cheap.txt");
FileOutputStream outFileStream2 = new FileOutputStream(outFile2);
PrintWriter outStream2 = new PrintWriter(outFileStream2);
computeAverage(bufReader, outStream1, outStream2, average);
}
public static void computeAverage(BufferedReader bufReader, PrintWriter outStream1, PrintWriter outStream2, double average) {
String line = "";
double mark = 0;
double sum = 0;
int count = 0;
try {
bufReader.readLine();
while ((line = bufReader.readLine()) != null) {
String [] data = line.split(" ");
mark = Double.parseDouble(data[2]);
sum += mark;
count++;
}
average = sum / count;
compareMark(outStream1, outStream2, average);
} catch (NumberFormatException | IOException e) {
System.out.println(e);
} finally {
if (bufReader != null) {
try {
bufReader.close();
} catch ( IOException e) {
e.printStackTrace();
}
}
}
}
public static void compareMark(PrintWriter outStream1, PrintWriter outStream2, double average) throws FileNotFoundException {
File inFile = new File("stationary.txt");
FileReader fileReader = new FileReader(inFile);
BufferedReader bufReader = new BufferedReader(fileReader);
String line = " ";
double sum = 0;
double mark = 0;
int count = 0;
try {
double ave = (double) Math.round(average * 100) / 100;
System.out.println("another " + ave);
bufReader.readLine();
while ((line = bufReader.readLine()) != null) {
System.out.println(line);
String [] data = line.split(" ");
mark = Double.parseDouble(data[2]);
if (mark > ave) {
System.out.println("Over");
outStream1.write(line);
} else {
System.out.println("Less");
outStream2.write(line);
}
}
} catch (IOException e) {
System.out.println(e);
} catch (NumberFormatException ex) {
System.out.println(ex);
} finally {
if (bufReader != null) {
try {
bufReader.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
The source code is perfectly working, just that I received 0 bytes of both files after executing reading twice (first, doing average and last, doing comparison). Why is that? what am I doing wrong here?
Thank you for your kind help.
Your code is not correct and does not compile. But the main flaws are the following:
Your Double.parseDouble(data[2]) shouldn't work with your 4th line of data. Better use Double.parseDouble(data[data.length - 1])
Remove the readLine()-calls in front of the while-loop.
Write the lines including a line separator.
Close the OutStreams
The Data File that you have provided have the columns seperated by a space. As the 2nd Column has data which contains spaces, the convertion of data[2] to double will trigger an exception. Which will make the program to close the buffers and exit.
Use Commas to seperate column data.
Use better exception handling to find exceptions easily.
All you need is to close those output stream. As you are using bufferredWriter and not flushing it after each write you need to close those output-stream. which will write back those lines or datas into the file. Here is an example how you can do it:
Example 1: using flush().
....
outStream1.write(line);
outStream1.flush();
} else {
System.out.println("Less");
outStream2.write(line);
outStream2.flush();
}
Example 2: most efficient (either way you need to close those buffer too like bufReader.close())
...
} catch (IOException e) {
System.out.println(e);
} catch (NumberFormatException ex) {
System.out.println(ex);
} finally {
// add try catch.
outStream2.close();
outStream1.close();
if (bufReader != null ... ) {
try {
bufReader.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
As requested, an example using List
First a class to hold the stationary data, must be completed:
public class Stationary {
private final int id; // or String if desired
private final String name;
private final double mark; // BigDecimal would be better for money
public Stationary(int id, String name, double mark) {
// TODO error checking
this.id = id;
...
}
public int getId() {
return id;
}
... // TODO other getters
// TODO equals, hashCode, toString
}
and to read the file:
public List<Stationary> read(File file) {
List<Stationary> list= new ArrayList<>();
try (BufferedReader reader = new BufferedReader(new FileReader(file))) {
String line;
while ((line = reader.readLine()) != null) {
// TODO parse line into id, name, mark
list.add(new Stationary(id, name, mark);
}
}
return list;
}
now the list can be used as needed, e.g. average:
List<Stationary> stationaries = read(STATIONARY_FILE);
...
for (Stationary stationary : stationaries) {
sum += stationary.getMark();
count += 1;
}
...
streams not used to keep it simple

Concatenate multiple files

I am trying to concatenate multiple text files. The program is working correctly, but if I do not know the total number of files, then how should the for loop be changed?
public class MultipleMerge {
public static void main(String[] args) {
BufferedReader br = null;
BufferedWriter bw = null;
String inFileName = "C:\\Users\\dokania\\Desktop\\Bio\\Casp10\\fasta\\out";
File file = new File("C:\\Users\\dokania\\Desktop\\New folder\\out.txt");
try {
String s;
int fileCounter = 0;
FileWriter fw = new FileWriter(file.getAbsoluteFile());
bw = new BufferedWriter(fw);
for (fileCounter = 0; fileCounter < 157; fileCounter++) {
br = new BufferedReader(new FileReader(inFileName + (fileCounter++) + ".fa"));
while ((s = br.readLine()) != null) {
bw.write(s + "\n");
}
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (br != null) {
br.close();
bw.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
Try get an array of Files in directory:
File[] array = new File("C:\\Users\\dokania\\Desktop\\Bio\\Casp10\\fasta\\").listFiles();
And then go through all files using foreach cycle
for(File file:array){
//...
}
Maybe you'll need to use FileFilter:
http://docs.oracle.com/javase/7/docs/api/java/io/FileFilter.html
in method listFiles()
You could use command line arguments:
public class CommandLineTest {
public static void main(String[] args) {
int howManyFiles = Integer.parseInt(args[0]);
}
}
Above code gives you the first command line argument and treats it as an integer. In your code, you should check if there really is an integer specified, though.

How to check if txt file contains a String, if so don't duplicate it

So right now I'm making a mod in Minecraft where it takes everyones username from a server and adds it to a txt file, it works but the the problem is I don't want to duplicate the names when I use the command again. Nothing has worked so far. How would I check if the txt already contains the username, don't add it again? Thank you. Again, I need it to before writing another name to the list, check the txt file if it already contains the name, if so don't add it.
for (int i = 0; i < minecraft.thePlayer.sendQueue.playerInfoList.size(); i++) {
List playerList = minecraft.thePlayer.sendQueue.playerInfoList;
GuiPlayerInfo playerInfo = (GuiPlayerInfo) playerList.get(i);
String playerName = StringUtils.stripControlCodes(playerInfo.name);
try {
fileWriter = new FileWriter(GameDirectory() + "\\scraped.txt", true);
bufferedReader = new BufferedReader(new FileReader(GameDirectory() + "\\scraped.txt"));
lineNumberReader = new LineNumberReader(new FileReader(GameDirectory() + "\\scraped.txt"));
} catch (IOException e) {
e.printStackTrace();
}
printWriter = new PrintWriter(fileWriter);
try {
fileWriter.write(playerName + "\r\n");
lineNumberReader.skip(Long.MAX_VALUE);
} catch (IOException e) {
e.printStackTrace();
}
printWriter.flush();
}
addMessage("Scraped " + lineNumberReader.getLineNumber() + " usernames!");
EDIT: Really need an answer guys :( Thank you
EDIT: this is what I have now, but it's not even writing it anymore.
List playerList = minecraft.thePlayer.sendQueue.playerInfoList;
for (int i = 0; i < minecraft.thePlayer.sendQueue.playerInfoList.size(); i++) {
GuiPlayerInfo playerInfo = (GuiPlayerInfo) playerList.get(i);
String playerName = StringUtils.stripControlCodes(playerInfo.name);
String lines;
try {
if ((lines = bufferedReader.readLine()) != null) {
if (!lines.contains(playerName)) {
bufferedWriter.write(playerName);
bufferedWriter.newLine();
bufferedWriter.flush();
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
int linenumber = 0;
try {
while (lineNumberReader.readLine() != null) {
linenumber++;
}
} catch (IOException e) {
e.printStackTrace();
}
The logic of your second piece of code is wrong. If you write out the pseudo-code of it, it's easy to see why:
Open a File Reader at the start of the file
For every Player on the server
Save the player name
Read the next line of the file
If we have not reached the end of the file
If the player name is not on this line of the file
Write the name of the player to the file
You need to read the entire file outside of the loop, and then check if the player exists anywhere in the file, not just if it happens to be on the line which is the same position as the player on the server.
The easiest way to do this is to keep the players in a list while you're processing, and read/write them to file, like this:
public static List<String> loadPlayerList() throws FileNotFoundException
{
final Scanner scanner = new Scanner(new File(GameDirectory() + "\\scraped.txt"));
final List<String> players = new ArrayList<>();
while(scanner.hasNextLine())
players.add(scanner.nextLine());
return players;
}
public static void writePlayersList(final List<String> players) throws IOException
{
try(final BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(
new FileOutputStream((GameDirectory() + "\\scraped.txt")))))
{
for(final String player : players)
{
writer.write(player);
writer.newLine();
}
}
}
public static void main(String[] args) throws IOException
{
final List<String> players = loadPlayerList();
for(final GuiPlayerInfo player : minecraft.thePlayer.sendQueue.playerInfoList)
{
final String playerName = StringUtils.stripControlCodes(player.name);
if(!players.contains(playerName))
players.add(playerName);
}
writePlayersList(players);
}

Issue with using an array to store/print files from Linux

I cant figure out how to loop through this instead of just repeating the code, bugging the hell outta me! FYI assignment has already been turned in using 5 iterations of code, just wanted to learn how to implement the string array holding file contents into a for loop for future knowledge. I have tried for a few hours but it just prints the filename, cant seem to get the file contents.
/*************************************************************************
* LinuxSys.java
*
* This program reads text from a file
**************************************************************************/
import java.util.*;
import java.io.*;
public class LinuxSys {
public static void main (String[] args) {
String systemInfo[] = new String [5];
int i = 0;
// using _ to simulate file paths to test on local cpu, as it is easier/quicker
// than logging onto server/copy pasting code into new pico file
systemInfo[0] = "_proc_sys_kernel_hostname.txt"; //local files
systemInfo[1] = "_proc_meminfo.txt"; //local files
systemInfo[2] = "_proc_version.txt"; //local files
systemInfo[3] = "_proc_sys_kernel_hostname.txt"; //local files
//systemInfo[0] = "_proc_sys_kernel_hostname.txt"; //local files
// 1st try to print server host name file
try {
BufferedReader inputStream =
new BufferedReader(new FileReader(systemInfo[i]));
String line = "blank";
while (line != null) {
if((line = inputStream.readLine()) != null) {
System.out.println(line);
i++; // increment systemInfo[] array position
} // end if
} //end while
System.out.println(); // create space
inputStream.close();
} // end try
catch(FileNotFoundException e) {
System.out.println("File was not found");
System.out.println("or could not be opened");
} //end catch
catch(IOException e) {
System.out.println("Error reading from file");
} //end catch
// 2nd try to print server memory file
{
BufferedReader inputStream =
new BufferedReader(new FileReader(systemInfo[i]));
String line = "blank";
while (line != null) {
if((line = inputStream.readLine()) != null) {
System.out.println(line);
i++; // increment systemInfo[] array position
} // end if
} //end while
System.out.println(); // create space
inputStream.close();
} // end try
catch(FileNotFoundException e) {
System.out.println("File was not found");
System.out.println("or could not be opened");
} //end catch
catch(IOException e) {
System.out.println("Error reading from file");
} //end catch
// 3rd try to print version file
try {
BufferedReader inputStream =
new BufferedReader(new FileReader(systemInfo[i]));
String line = "blank";
while (line != null) {
if((line = inputStream.readLine()) != null) {
System.out.println(line);
i++;
} // end if
} //end while
System.out.println(); // create space
inputStream.close();
} // end try
catch(FileNotFoundException e) {
System.out.println("File was not found");
System.out.println("or could not be opened");
} //end catch
catch(IOException e) {
System.out.println("Error reading from file");
} //end catch
} // end main
} // end class
for(int i=0; i < systemInfo.size; ++i)
{
// the code you want to repeat with i varying each time
}
or
int i=0;
while(i < systemInfo.size)
{
// the code you want to repeat with i varying each time
++i;
}
or
int i=0;
while(i++ < systemInfo.size)
{
// the code you want to repeat with i varying each time
}
or
int i=0;
do
{
// the code you want to repeat with i varying each time
}
while(++i < systemInfo.size)
or...

Categories