I know there are many questions about reading text files here but I have gone through all of them and I think I'm having some difficulty with syntax or SOMETHING because nothing that I've been trying has been working at all.
What I'm attempting to do is this:
1) read a text file inputed by user
2) copy each individual line into an array, so each line is its own element in the array
I feel like I am very close but for some reason I can't figure out exactly how to get it to work!
Here is the relevant code I have right now:
I keep getting out of bounds exceptions in three locations which I've marked off.
Been working on this for quite a while not sure what to do next! Any ideas?
import java.io.IOException;
import java.util.Scanner;
public class FindWords {
public static void main (String args[]) throws IOException{
FindWords d = new Dictionary();
((Dictionary) d).dictionary(); //********* out of bounds here
}
/**
* Validates and returns the dictionary inputed by the user.
*
* #param
* #return the location of the dictionary
*/
public static String getDict(){
///////////////////ASK FOR DICTIONARY////////////////////
System.out.println("Please input your dictionary file");
//initiate input scanner
Scanner in = new Scanner(System.in);
// input by user
String dictionary = in.nextLine();
System.out.println("Sys.print: " + dictionary);
//make sure there is a dictionary file
if (dictionary.length() == 0){
throw new IllegalArgumentException("You must enter a dictionary");
}
else return dictionary;
}
}
which calls on the class Dictionary:
import java.io.*;
public class Dictionary extends FindWords{
public void dictionary () throws IOException{
String dict = getDict();
String[] a = readFile(dict); //********** out of bounds here
int i = 0;
while(a[i] != null){
System.out.println(a[i]);
i++;
}
}
public static String[] readFile(String input) throws IOException{
//read file
BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(input)));
System.out.println ();
int count = 0;
String[] array = new String[count];
try{
while (br.readLine() != null){
array[count] = br.readLine(); //********out of bounds here
count++;
}
br.close();
}
catch (IOException e){
}
return array;
}
}
Thank you for looking!
Edit: Just fyi: I have my .txt file in the parent project folder.
Have you tried this?:
List<String> lines = Files.readAllLines(Paths.get("/path/to/my/file.txt"));
and then transform your list to an array if you want:
String[] myLines = lines.toArray(new String[lines.size()]);
You start with an array size of zero...
int count = 0;
String[] array = new String[count];
Several issues here :
In Java, you can't expand arrays, i.e you have to know their length in advance when you instantiate them. Hence the ArrayOutOfBoundException. To make this easy, I suggest that you use an ArrayList instead.
In your while loop, you're making 2 calls to br.readLine(), so basically you're skipping one line out of 2.
You are initializing a zero-length array, hence the exception on the first iteration:
int count = 0;
String[] array = new String[count];
Since you probably don't know the expected size, work with a List instead:
List<String> list = new ArrayList<>();
String thisLine = null;
try{
while ((thisLine = br.readLine()) != null) {
list.add(thisLine);
}
}
You can get the total size afterwards by:
list.size();
Or even better, go with morganos solution and use Files.readAllLines().
Related
I am trying to print the contents of an arraylist that I am using to store arrays of strings. Basically, I am trying to write a program that reads a file line by line, and stores the individual lines as separate arrays of strings in an arraylist. I want to check if it worked by printing the string arrays in the arraylist but currently my code is only printing the addresses. It looks like the following:
package Filecheck;
import java.io.*;
import java.util.ArrayList;
import java.util.Iterator;
public class FileImport {
public static void main(String [] args) {
// The name of the file to open.
String fileName = "/Users/Frank/Desktop/test.rtf";
String line;
String[] name = null;
ArrayList<String[]> list = new ArrayList<String[]>();
try {
FileReader fileReader = new FileReader(fileName);
BufferedReader readerB = new BufferedReader(fileReader);
line = readerB.readLine();
while((line = readerB.readLine()) != null) {
System.out.println(line);
name = line.split(" ");
list.add(name);
}
for (int i=0; i < list.size(); i++){
System.out.println(list.get(0).toString());
}
readerB.close();
}
catch(FileNotFoundException ex) {
System.out.println(
"Unable to open file '" +
fileName + "'");
}
catch(IOException ex) {
System.out.println(
"Error reading file '"
+ fileName + "'");
}
}
}
The output of the code is as follows:
{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
{\colortbl;\red255\green255\blue255;}
\margl1440\margr1440\vieww10800\viewh8400\viewkind0
\pard\tx720\tx1440\tx2160\tx2880\tx3600\tx4320\tx5040\tx5760\tx6480\tx7200\tx7920\tx8640\pardirnatural
\f0\fs24 \cf0 \
Test String The pens are going to win the cup\
Another Test}
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
[Ljava.lang.String;#533ded59
Any help would be greatly appreciated. Thank you!
Some easy options for this. There are a bunch of ways to do this and I can't cover all of them.
1) Consider whether you need to be storing a list of String arrays and instead just store a list of strings.
2) Create your own print array function and call that for each element as you iterate the array. An example implementation of this function could be
public void printArray(T[] array) {
for(T item : array) System.out.println(item);
}
3) Convert your array or strings to a list of strings
This is a project i'm working on at college, everything seems good except in the game class which initializes the game. Here is a snippet
public class Game{
private Player player;
private World world;
private ArrayList<NonPlayableFighter> weakFoes;
private ArrayList<NonPlayableFighter> strongFoes;
private ArrayList<Attack> attacks;
private ArrayList<Dragon> dragons;
public Game() throws IOException{
player = new Player("");
world = new World();
weakFoes = new ArrayList<NonPlayableFighter>();
strongFoes = new ArrayList<NonPlayableFighter>();
attacks = new ArrayList<Attack>();
dragons = new ArrayList<Dragon>();
loadAttacks ("Database-Attacks_20309.csv");
loadFoes ("Database-Foes_20311.csv");
loadDragons ("Database-Dragons_20310.csv");
}
after that follows some getters and the 4 method i am supposed to implement.
These methods are loadCSV(String filePath),loadAttacks(String filePath),loadFoes(String filePath),loadDragons(String filePath)
I have created loadCSV(String filePath) such that it returns an ArrayList of String[] here:
private ArrayList<String[]> loadCSV(String filePath) throws IOException{
String currentLine = "";
ArrayList<String[]> result = new ArrayList<String[]>();
FileReader fileReader = new FileReader(filePath);
BufferedReader br = new BufferedReader(fileReader);
currentLine = br.readLine();
while (currentLine != null){
String[] split = currentLine.split(",");
result.add(split);
}
br.close();
return result;
}
Then i would like to load some attacks, foes, and dragons and inserting them in the appropriate ArrayList.
I applied loadAttacks(String filePath) here:
private void loadAttacks(String filePath) throws IOException{
ArrayList<String[]> allAttacks = loadCSV(filePath);
for(int i = 0; i < allAttacks.size(); i++){
String[] current = allAttacks.get(i);
Attack temp = null;
switch(current[0]){
case "SA": temp = new SuperAttack(current[1],
Integer.parseInt(current[2]));
break;
case "UA": temp = new UltimateAttack(current[1],
Integer.parseInt(current[2]));
break;
case "MC": temp = new MaximumCharge();
break;
case "SS": temp = new SuperSaiyan();
break;
}
attacks.add(temp);
}
}
I wrote it such that it takes the ArrayList returned from loadCSV(String filePath) and searches in each String[] within the ArrayList on the first String using a switch thus creating the appropriate attack and adding it to attacks.
Then i would like to read another CSV for the Foes and the CSV file is structured such that in the first line there are some attributes the second line some attacks of type SuperAttack and the third line holds some attacks of type Ultimate attack. Also within each foe there is a boolean attribute that determines if it is a Strong or Weak Foe thus putting it in the right Arraylist. Here is the code for loadFoes(String filePath):
private void loadFoes(String filePath) throws IOException{
ArrayList<String[]> allFoes = loadCSV(filePath);
for(int i = 0; i < allFoes.size(); i += 3){
String[] current = allFoes.get(i);
String[] supers = allFoes.get(i+1);
String[] ultimates = allFoes.get(i+2);
ArrayList<SuperAttack> superAttacks = new ArrayList<SuperAttack>();
ArrayList<UltimateAttack> ultimateAttacks = new ArrayList<UltimateAttack>();
NonPlayableFighter temp = null;
for(int j = 0; i < supers.length; j++){
int index = attacks.indexOf(supers[j]);
if(index != -1){
superAttacks.add((SuperAttack)attacks.get(index));
}
else break;
}
for(int j = 0; i < ultimates.length; j++){
int index = attacks.indexOf(ultimates[j]);
if(index != -1){
ultimateAttacks.add((UltimateAttack)attacks.get(index));
}
else break;
}
if(current[7].equalsIgnoreCase("True")){
temp = new NonPlayableFighter(current[0], Integer.parseInt(current[1]),
Integer.parseInt(current[2]), Integer.parseInt(current[3]),
Integer.parseInt(current[4]), Integer.parseInt(current[5]),
Integer.parseInt(current[6]), true, superAttacks, ultimateAttacks);
strongFoes.add(temp);
}
else{
temp = new NonPlayableFighter(current[0], Integer.parseInt(current[1]),
Integer.parseInt(current[2]), Integer.parseInt(current[3]),
Integer.parseInt(current[4]), Integer.parseInt(current[5]),
Integer.parseInt(current[6]), false, superAttacks, ultimateAttacks);
weakFoes.add(temp);
}
}
}
First i get the first three String[] in the ArrayList returned from loadCSV(String filePath and made 2 loops to check if the attacks are within the previously loaded attacks CSV then i check for the attribute that determines if it is a strong or weak and accordingly creating a new NonPlayableFighter and adding it to the appropriate list.
Running the jUnit4 tests for this assignment it gives me a Compilation Error: Unhandled exception type IOException. And generally speaking does the code have any notable problems ?
It's better to reuse already exist CSV file readers for Java (e.g. CVSReader) if isn't a part of you task.
That makes a lot of code. I'll answer to your Compilation Error.
While reading a file you have to pu your code in a try catch in order to avoid this kind of error. In your loadCSV method you have to set up a try catch block.
Please refer to this site for complete tutorial.
try (BufferedReader br = new BufferedReader(new FileReader("C:\\testing.txt")))
{
String sCurrentLine;
while ((sCurrentLine = br.readLine()) != null) {
String[] split = currentLine.split(",");
result.add(split);
}
} catch (IOException e) {
e.printStackTrace();
}
To make it short, code that access to files have to be in a try catch to avoid IO Exception, or be in a method that throws the exception (but then it has to be catched elsewhere).
In that code you have a good example of a try-with-resource, very good way to manage your ressource and memory.
loadCSV(String filePath) is a infinite loop isn't it? And as for the IOException it as #RPresle suggested a try/catch would do the trick around the BufferedReader.
we are trying to compare two string arrays( as[ ] and bs[ ]) and update the array string as[ ] with the new strings present in bs[ ] .We are not able to update the as[ ].Pls help us with the following codes.Thank u;)
public class Aa {
/**
* #param args the command line arguments
*/
public static void main(String[] args) {
// Create an array of 4 strings (indexes 0 - 3)
String as[] = new String[5];
String bs[] = new String[16];
int i;
try {
// Create a bufferreader object to read our file with.
BufferedReader reader = new BufferedReader(new FileReader("input.txt"));
BufferedReader reader1;
reader1 = new BufferedReader(new FileReader("a1.txt"));
// Line will hold our line read from the file
String line = "";
String line1 = "";
// The counter will keep track of how many lines we have read
int counter = 0;
int counter1 = 0;
// Read in a line from the file and store it in "line". Do this while we don't hit null or while the counter is less than 4.
// The counter prevents us from reading in too many lines.
while (((line = reader.readLine()) != null) && (counter < 4)) {
as[counter] = line;
counter++;
}
while (((line1 = reader1.readLine()) != null) && (counter1 < 16)) {
bs[counter1] = line1;
counter1++;
}
System.out.println("value"+as[0]);
System.out.println("value"+bs[0]);
int temp,temp1,j;
temp=as.length;
temp1=bs.length;
System.out.println("length:"+temp);
System.out.println("length1:"+temp1);
for(i=0;i<bs.length;i++)
{
for(j=0;j<as.length;j++)
{
if(as[j].equals(bs[i]))
{
//ignore
}
else
{
temp++;
as[temp]=bs[i];
}
}
}
// With a foreach style loop we loop through the array of strings and print them out to show they were read in.
reader1.close();
reader.close();
}
catch (Exception ex) { System.out.println("Exception: " + ex.getMessage()); }
}
}
Since you are using two arrays containing only strings, its better to convert both to list and add
List aList = (Arrays.asList(as));
List bList = (Arrays.asList(bs));
bList.removeAll(aList); // assuming you have some common objects in both
aList.addAll(bList);
as = aList.toArray(); // Convert back to array
Take a look at Apache Commons ArrayUtils:
You can use the combination of contains and a third temporary Array to store the differences (i.e. !contains).
Thanks.
else
{
temp++;
as[temp]=bs[i];
}
This doesn't work at Java as Thilo said in comments. You can not increase size of an array once its size is set.
I suggest to use ArrayList instead of array. You can simply add new items to an array list without any problem.
If you insist on using arrays, you can create a longer new array and copy your old array in here and add your new element. I wouldn't recommend this.
Importing a large list of words and I need to create code that will recognize each word in the file. I am using a delimiter to recognize the separation from each word but I am receiving a suppressed error stating that the value of linenumber and delimiter are not used. What do I need to do to get the program to read this file and to separate each word within that file?
public class ASCIIPrime {
public final static String LOC = "C:\\english1.txt";
#SuppressWarnings("null")
public static void main(String[] args) throws IOException {
//import list of words
#SuppressWarnings("resource")
BufferedReader File = new BufferedReader(new FileReader(LOC));
//Create a temporary ArrayList to store data
ArrayList<String> temp = new ArrayList<String>();
//Find number of lines in txt file
String line;
while ((line = File.readLine()) != null)
{
temp.add(line);
}
//Identify each word in file
int lineNumber = 0;
lineNumber++;
String delimiter = "\t";
//assess each character in the word to determine the ascii value
int total = 0;
for (int i=0; i < ((String) line).length(); i++)
{
char c = ((String) line).charAt(i);
total += c;
}
System.out.println ("The total value of " + line + " is " + total);
}
}
This smells like homework, but alright.
Importing a large list of words and I need to create code that will recognize each word in the file. What do I need to do to get the program to read this file and to separate each word within that file?
You need to...
Read the file
Separate the words from what you've read in
... I don't know what you want to do with them after that. I'll just dump them into a big list.
The contents of my main method would be...
BufferedReader File = new BufferedReader(new FileReader(LOC));//LOC is defined as class variable
//Create an ArrayList to store the words
List<String> words = new ArrayList<String>();
String line;
String delimiter = "\t";
while ((line = File.readLine()) != null)//read the file
{
String[] wordsInLine = line.split(delimiter);//separate the words
//delimiter could be a regex here, gotta watch out for that
for(int i=0, isize = wordsInLine.length(); i < isize; i++){
words.add(wordsInLine[i]);//put them in a list
}
}
You can use the split method of the String class
String[] split(String regex)
This will return an array of strings that you can handle directly of transform in to any other collection you might need.
I suggest also to remove the suppresswarning unless you are sure what you are doing. In most cases is better to remove the cause of the warning than supress the warning.
I used this great tutorial from thenewboston when I started off reading files: https://www.youtube.com/watch?v=3RNYUKxAgmw
This video seems perfect for you. It covers how to save file words of data. And just add the string data to the ArrayList. Here's what your code should look like:
import java.io.*;
import java.util.*;
public class ReadFile {
static Scanner x;
static ArrayList<String> temp = new ArrayList<String>();
public static void main(String args[]){
openFile();
readFile();
closeFile();
}
public static void openFile(){
try(
x = new Scanner(new File("yourtextfile.txt");
}catch(Exception e){
System.out.println(e);
}
}
public static void readFile(){
while(x.hasNext()){
temp.add(x.next());
}
}
public void closeFile(){
x.close();
}
}
One thing that is nice with using the java util scanner is that is automatically skips the spaces between words making it easy to use and identify words.
So I need to do exactly what it says in the title, take a text file called "words.txt", have the program read it, take all the words in it, and store them into an array. After that, the program needs to pick one out randomly, and print it in reverse. I'm having a lot of trouble getting it to work, as it always crashes at the end. Here's what I got so far:
import java.io.*;
import java.util.Random;
public class wordReader{
public static void main (String args[]) throws Exception{
BufferedReader br = new BufferedReader(new FileReader("words.txt"));
String strLine;
String[] filearray;
filearray = new String[10];
while ((strLine = br.hasNextLine())) {
for (int j = 0; j < filearray.length; j++){
filearray[j] = br.readLine();
System.out.println(filearray);
}
}
}
}
Alright, this i what I have at the moment:
import java.io.*;
import java.util.Random;
public class wordReader{
public static void main (String args[]) throws Exception{
BufferedReader br = new BufferedReader(new FileReader("words.txt"));
String strLine;
String[] filearray;
filearray = new String[10];
int j = 0;
int i = 0;
Random r = new Random();
while(((strLine = br.readLine()) !=null) && j < filearray.length){
filearray[j++] = strLine;
int idx = r.nextInt(filearray.length);
}
}
}
You can do this easily using the new Files API and StringBuilder to reverse your String. It will cut down your lines of code significantly.
public static void main(String[] args) throws Exception {
Path path = Paths.get("words.txt");
Charset charset = StandardCharsets.UTF_8;
String content = new String(Files.readAllBytes(path), charset);
String[] words = content.split(",|\.|\s+");
int randomIndex = new Random().nextInt(words.length);
String word = words[randomIndex];
String reversed = StringBuilder(word).reverse().toString();
System.out.println(reversed);
}
Try using the StringTokenizer to read the line.
http://docs.oracle.com/javase/7/docs/api/java/util/StringTokenizer.html
StringTokenizer st = new StringTokenizer("this is a test");
while (st.hasMoreTokens()) {
System.out.println(st.nextToken());
}
Lot's of ways to accomplish this. Here's a recursive method that prints as the calls are popping off the return stack. This was adapted from Reversing Lines With Recursion Java
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.PrintWriter;
public class ReverseLines {
public static BufferedReader input;
public static PrintWriter output;
public static void main(String[] args) throws Exception {
input = new BufferedReader(new FileReader("/tmp/words.txt"));
output = new PrintWriter(System.out);
reverse(input, output);
input.close();
output.flush();
output.close();
}
public static void reverse(BufferedReader input, PrintWriter output)
throws Exception {
String line = input.readLine();
if (line != null) {
reverse(input, output);
output.println(line);
}
}
}
You don't seem to have gotten to the point of doing the random index selection or the line reversal yet, so I won't address that stuff here. There are endless duplicates all over StackOverflow to tell you how to reverse a String.
At the moment, you're getting compile errors because (among other things) you're trying to use a method (BufferedReader#hasNextLine()) that doesn't exist. It looks like you were mixing up a couple of other approaches that you might have found, e.g.:
int j = 0;
while ((strLine = br.readLine()) != null) { // Set strLine to the next line
filearray[j++] = strLine; // Add strLine to the array
// I don't recommend printing the whole array on every pass through the loop...
}
You'll notice that I also took out your inner for loop, because it was just setting every element of your list to the most recent line on every iteration. I'm assuming you wanted to populate the list with all of your lines. Realistically, you should also check whether j is in an acceptable range as well:
while (((strLine = br.readLine()) != null) && j < filearray.length) {...}
Note that realistically, you'd almost certainly be better off using a List to store your lines, so you could just add all the lines to the List and not worry about the length:
List<String> contents = new ArrayList<String>();
while ((strLine = br.readLine()) != null) {
contents.add(strLine); // Add strLine to the List
}
But, this does smell like homework, so maybe you're required to use a String[] for whatever reason.
Finally, there's a discrepancy between what you've written in your question and what your program looks like it's intended to do. You claim that you need a list of each word, but it looks more like you're trying to create a list of each line. If you need words instead of lines, you'll need to split up each line and add each token to the list.