This code takes two txt files, reads them puts them in 2d arrays and should check if the numbers in the files are magic squares but it keeps returning NumberFormatException error. I'm new to java so if anyone could help me that would be great. I'm pretty sure the problem come from the txt file being string and the 2d array needing to be in int form. But how and where do I make that conversion on my code?
this is what i have:
import java.io.File;
import java.io.FileNotFoundException;
import java.util.Arrays;
import java.util.Scanner;
public class ms {
public static void main(String[] args) throws FileNotFoundException {
String filename1 = "magicSquaresData.txt", filename2 = "magicSquaresData.txt";
int nos[][] = null;
nos = getArray(filename1);
boolean b = isMagicSquare(nos);
printArray(nos);
if (b) {
System.out.println("It is a magic Square");
} else {
System.out.println("It is not a magic Square");
}
System.out.println("\n");
nos = getArray(filename2);
b = isMagicSquare(nos);
printArray(nos);
if (b) {
System.out.println("It is a magic Square");
} else {
System.out.println("It is not a magic Square");
}
}
private static int[][] getArray(String filename) throws FileNotFoundException {
String line;
int nos[][] = null;
int size = 0, rows = 0;
Scanner sc = null;
try {
sc = new Scanner(new File(filename));
while (sc.hasNext()) {
if (!sc.nextLine().isEmpty())
size++;
}
sc.close();
nos = new int[size][size];
sc = new Scanner(new File(filename));
while (sc.hasNext()) {
line = sc.nextLine();
if (!line.isEmpty()) {
String arr[] = line.split("\t");
for (int i = 0; i < arr.length; i++) {
nos[rows][i] = Integer.valueOf(arr[i]);
}
rows++;
}
}
sc.close();
} catch (FileNotFoundException e) {
System.out.println(e);
}
return nos;
}
private static void printArray(int[][] nos){
for(int i = 0; i<nos[0].length;i++) {
for (int j = 0; j < nos[0].length; j++){
System.out.printf("%-3d",nos[i][j]);
}
System.out.println();
}
}
private static boolean isMagicSquare(int[][] square) {
boolean bool = true;
int order = square.length;
int[] sumRow = new int[order];
int[] sumCol = new int[order];
int[] sumDiag = new int[2];
Arrays.fill(sumRow, 0);
Arrays.fill(sumCol, 0);
Arrays.fill(sumDiag, 0);
for (int row = 0; row < order; row++){
for (int col = 0; col < order; col++) {
sumRow[row] += square[row][col];
}
}
for (int col = 0; col < order; col++) {
for (int row = 0; row < order; row++) {
sumCol[col] += square[row][col];
}
}
for (int row = 0; row < order; row++) {
sumDiag[0] += square[row][row];
}
for (int row = 0; row < order; row++) {
sumDiag[1] += square[row][order - 1 - row];
}
bool = true;
int sum = sumRow[0];
for (int i = 1; i < order; i++) {
bool = bool && (sum == sumRow[i]);
}
for (int i = 0; i < order; i++) {
bool = bool && (sum == sumCol[i]);
}
for (int i = 0; i < 2; i++) {
bool = bool && (sum == sumDiag[i]);
}
return bool;
}
}
SUGGESTION:
Substitute nos[rows][i] = Integer.valueOf(arr[i]); for a custom method that will tell you WHERE the error is occurring.
EXAMPLE:
public static Integer tryParse(String text, int row, int i) {
try {
return Integer.parseInt(text);
} catch (NumberFormatException e) {
System.out.println("ERROR: row=" + row + ", i=" + i + ", text=" + text);
return null;
}
}
CAVEAT: This is for helping you troubleshoot ONLY. You definitely wouldn't want to release this in "production code" ;)
What is the NumberFormatException?
Thrown to indicate that the application has attempted to convert a string to one of the numeric types, but that the string does not have the appropriate format.
Offtopic:
A thing that i can notice is that both filesnames have the same name. So you will verify the same file 2 times.
String filename1 = "magicSquaresData.txt", filename2 = "magicSquaresData.txt";
I checked your program and you error appears when you put like this on a file:
1. 5 5
2. 5 5
So the error shows beacause you are trying to parse to int the String "5 5". So your code pick the all line and tries to convert to int and " " it's not an int. And there lives the NumberFormatException error.
How do to solve it?
The function that we will work on is the one that you pass from file to an array in
private static int[][] getArray(String filename) throws FileNotFoundException{
The of the function is after we read the file.
As you said, you are leading with a 2d array so to insert all the numbers we need to have loops for each dimension on the array.
So we will start from there.
I will use a while beacause we are dealing with a string and it's easier to verify the text that its left on the line. Will add a new int variable that starts in 0 to pass in every column of a line to use with the while loop. And with this we got this:
for (int i = 0; i < lines.length; i++) {
while(!"".equals(line)){
whileIterator++;
}
whileIterator = 0;
}
Next setep, we will divide in 2 behaviors because we will substring the String that has in the line, and will work differently when it's the last number that we are verifying:
for (int i = 0; i < lines.length; i++) {
while(!"".equals(line)){
if(whileIterator + 1 == size){//If its the last iteration that we need in a line
}else{//All other iterations
whileIterator++;
}
whileIterator = 0;}
To finalize let's add the new logic to insert in nos array. So lets pick all line for example 2 7 6 and we want to add the number 2, so lets do that. You just need to substring(int startIndex, int finalIndex) the line and add to the nos array. After that let remove the number and the space ("2 ") from the line that we are veryfying.
for (int i = 0; i < lines.length; i++) {
while(!"".equals(line)){
if(whileIterator + 1 == size){//If its the last iteration that we need
nos[rows][whileIterator] = Integer.parseInt(line.substring(0));//Add to array
line = "";//To not pass the while verification
}else{//All other iterations
nos[rows][whileIterator] = Integer.parseInt(line.substring(0, line.indexOf(" ")));//Add to array
line = line.substring(line.indexOf(" ") + 1);//remove the number we added behind
}
whileIterator++;
}
whileIterator = 0;}
And here you go, that how you add the numbers to an array and don't get the error.
If you need some further explanation just ask. Hope it helps :)
I'm a beginner in java and I am trying to fill a 2d character array from an input file. To do this I constructed a method which takes in a 2d character array as a parameter variable, then reads the file and stores it as a character array. So far I have done everything except fill the array, as when I run the code the program throws a NoSuchElement exception. If anyone could help me with this I would greatly appreciate it.
public static char [][] MakeWordArray (char [][] givenArray)
{
try
{
File wordFile= new File ("words.txt");
Scanner in= new Scanner (wordFile);
int rows =0;
int col=0;
while (in.hasNextLine())
{
rows = rows + 1;
col = col + 1;
in.next();
}
char [][] words = new char [rows][col];
File wordFile2= new File ("words.txt");
Scanner in2= new Scanner(wordFile2);
for ( int i = 0; i < rows; i++)
{
for (int j = 0; j < col; j++)
{
String wordly = in2.nextLine();
words [i][j] = wordly.charAt(i);
}
}
return words;
}
catch (FileNotFoundException e)
{
System.out.println("File Does Not Exist");
}
return null;
}
I think your counting methods have some problems.
If you want to count how many lines your .txt have:
int counter = 0;
while (in.hasNextLine())
{
counter++;
in.nextLine();
}
If you want to count how many char your .txt have:
int counterWithoutSpace = 0, counterWithSpace = 0;
while (in.hasNextLine())
{
String line = in.nextLine();
Scanner inLine = new Scanner(line);
while (inLine.hasNext())
{
String nextWord = inLine.next();
counterWithoutSpace += nextWord.length();
counterWithSpace += nextWord.length() + 1;
}
counterWithSpace--;
}
If you want to count how many char you have on each line, I recommend ArrayList. Because the size of your array is dynamic.
Note that you can also you can use the char counter logic above with List too.See as follows:
List<Integer> arr = new ArrayList<Integer>();
while (in.hasNextLine())
{
arr.add(in.nextLine().length());
}
And if you realy needs the static array, you can use:
Integer[] intArr = arr.toArray(new Integer[0]);
You can transform its entire function as below to get a list of every Character of the .txt:
List<Character> arr = new ArrayList<Character>();
while (in.hasNextLine())
{
String line = in.nextLine();
for (char c : line.toCharArray())
{
arr.add(c);
}
}
Try using a do while loop instead of the while
do
{
rows=rows+1;
col=lol+1;
in.next();
}
while(in.hasNext());
There are multiple questions here.
1) Why did you provide a char[][] parameter when you are not even using it?
2) Why are you using two files when all you need to do is read from a file and convert it in 2d Array?
3) The method name should follow camel casing convention.
From what i understood from your question, This is a code i've tried.
NOTE- because the requirement is of an Array and not dynamic datatypes like List ArrayList etc., the data entered into char array might be lost
Saying that here is what works.
public class StackOverflow{
public static char [][] makeWordArray ()
{
try{
File f = new File("C:\\docs\\mytextfile.txt");
Scanner scan = new Scanner(f);
int row = 0, col = 0;
String readData = "";
while(scan.hasNextLine()){
readData += scan.nextLine();
row++;
}
double range = (readData.length()/row);
col = (int)Math.ceil(range);
char[][] arr = new char[row][col];
int count = 0;
for (int i = 0; i < row; i++){
for(int j = 0; j < col; j++){
arr[i][j] = readData.charAt(count++);
System.out.println("Pos: ["+ i +"][" + j + "]" + arr[i][j]);
}
}
return arr;
}
catch(FileNotFoundException fe){
System.err.println(fe.getMessage());
return null;
}
}
public static void main(String[] arg){
char[][] myarr = StackOverflow.makeWordArray();
//print your array
}
}
I have a read() method and inside I want to separate the Strings(which have spaces between them) and putting them in a two dimensional array, but before that I get rid of all the spaces. After the array initialized, it is given to the CSV constructor and that is creating its own 2D array.
The problem is that I always get the following error: "variable sr might not have been initialized" at CSV csv = new CSV(sr).
How do I make sure that my array gets the valid String?
private String[][] tomb;
private CSV(String[][] t2) {
tomb = new String[t2.length][];
for(int i = 0; i < t2.length; i++) {
tomb[i] = new String[t2[i].length];
for(int j = 0; j < t2[i].length; j++) {
tomb[i][j] = t2[i][j];
}
}
}
public static CSV read(Scanner sc) {
String[][] sr;
int n = 0;
while (sc.hasNextLine())
{
String line = sc.nextLine();
String[] str = line.split(",");
sr = new String[str.length][];
for (int i = 0; i < str.length; i++) {
sr[i][n].replaceAll("\\s+","");
}
n++;
}
CSV csv = new CSV(sr);
return csv;
}
You can resolve the error by setting sr to null in the initialization:
String[][] sr = null;
If you want to make sure sr was set correctly, you can check if sr is still null after the while loop completes.
I am "attempting" to make a method that will take my string array and compare it to an answer key that I have imported from a data file. Every time I compile I get this incompatible data type error and it is saying that:
Found: java.lang.String
Required: java.lang.String[][]
Am I not doing that?
I have had no luck searching for a solution on here and on Google. They seem to be irrelevant to what I am trying to accomplish.
import java.util.*; // Allows for the input of a scanner method.
import java.io.*; // Allows for the inputting and outputting of a data file.
import java.lang.*; // Allows for the use of String Methods.
//////////////////////////////////////////////////////////////////////////////////////
public class TESTY
{
static Scanner testanswers;
static PrintWriter testresults;
public static void main(String[] args) throws IOException
{
testanswers = new Scanner(new FileReader("TestInput.dat"));
testresults = new PrintWriter("TestOutput.dat");
String StudentID;
String answers;
// Reads first two lines first to know how many records there are.
String answerKey = testanswers.nextLine();
int count = Integer.parseInt(testanswers.nextLine());
// Allocate the array for the size needed.
String[][] answerArray = new String[count][];
for (int i = 0; i < count; i++)
{
String line = testanswers.nextLine();
answerArray[i] = line.split(" ", 2);
}
for(int row = 0; row < answerArray.length; row++)
{
for(int col = 0; col < answerArray[row].length; col++)
{
System.out.print(answerArray[row][col] + " ");
}
System.out.println();
}
gradeData(answerArray, answerKey);
testanswers.close();
testresults.close();
}
///////////////////////////////////////////////////////////
//Method: gradeData
//Description: This method will grade testanswers showing
//what was missed, skipped, letter grade, and percentage.
///////////////////////////////////////////////////////////
public static double gradeData(String[][] answerArray, String answerKey)
{
String key;
double Points = 0;
StringBuilder[] wrongAnswers = new StringBuilder[answerArray.length];
for(int rowIndex = 0; rowIndex < answerArray.length; rowIndex++)
{
String studAnswers[][] = answerArray[rowIndex][1].replace(" ", "S");
for(int charIndex = 0; charIndex < studAnswers[rowIndex][1].length; charIndex++)
{
if(studAnswers[rowIndex][1].charAt(charIndex).equals(key.charAt(charIndex)))
{
Points += 2;
}
if(!studAnswers[rowIndex][1].charAt(charIndex).equals('S'))
{
Points --;
}
else
{
wrongAnswers.setcharAt(charIndex, 'X');
}
}
}
return Points;
}
To get a better idea of what I am doing here is my .dat file:
TFFTFFTTTTFFTFTFTFTT
5
ABC54301 TFTFTFTT TFTFTFFTTFT
SJU12874 TTTFFTFFFTFTFFTTFTTF
KSPWFG47 FT FT FTFTFFTTFFTF
PAR38501 FFFFFFFFFFFFFFFFFFFF
MCY19507 TTTT TTTT TTTT TT TT
This statement, for instance,
String studAnswers[][] = answerArray[rowIndex][1].replace(" ", "S");
gives the compilation error
Type mismatch: cannot convert from String to String[][]
because
answerArray[rowIndex][1].replace(" ", "S"); returns a String.
answerArray is a 2D String array.
answerArray[rowIndex][1] gets
a element from the array which is a string
answerArray[rowIndex][1].replace... replaces a character in that
String with another character, ending up as another String (with
the replaced character)
You are trying to assign it to a String array.
Also, you cannot use equals on primitives (int, char...). You need to use == for comparison.
String studAnswers[][] = answerArray[rowIndex][1].replace(" ", "S");
Here, studAnswers is declared as an array of arrays of Strings, and you initialize it with a String. Indeed, answerArray is an array of arrays of Strings, and answerArray[rowIndex][1] is thus a String. And you replace every white space in this String by an S, which returns another String.
That doesn't make sense.
I have to take in a 2d array and multiple each row of it by the other corresponding 2d array.
Here are the files:
Omaha,104,1218,418,216,438,618,274,234,510,538,740,540
Saint Louis,72,1006,392,686,626,670,204,286,236,344,394,930
Des Moines,116,1226,476,330,444,464,366,230,602,260,518,692
Chicago,408,948,80,472,626,290,372,282,488,456,376,580
Kansas City,308,1210,450,234,616,414,500,330,486,214,638,586
Austin,500,812,226,470,388,488,512,254,210,388,738,686
Houston,454,1086,430,616,356,534,218,420,494,382,476,846
New Orleans,304,1278,352,598,288,228,532,418,314,496,616,882
File Two:
Omaha,7.5
Saint Louis,10.5
Des Moines,8.5
Chicago,11.5
Kansas City,12.5
Austin,10.75
Houston,12.5
New Orleans,9.25
Example: When I compare array[0][0] to price[0][0] the strings match therefore I must take the whole ROW of array[0] and multiply each element by that of price[0][1] to update the array.
Now here is my code:
public static String [][] updateString(String[][] array, String[][] prices)
{
String [][] newArray = new String[array.length][];
for(int row = 0; row < array.length; row++)
{
if (array[row][0].equals(prices[row][0]))
{
for(int i = 0; i<array.length; i++)
{
Double d=Double.parseDouble(array[row][i+1]) * Double.parseDouble(prices[row][1]);
newArray[row][i+1] = d.toString();
}
}
}
return newArray;
}
Here are my errors I'm getting:
Exception in thread "main" java.lang.NullPointerException
at assign_1.DansUtilities.updateString(DansUtilities.java:430)
at assign_1.SalesReportGenerator.main(SalesReportGenerator.java:50)
**line 430 is my method. line 50 is where I call it.
new code:
public static String [][] updateString(String[][] array, String[][] prices)
{
for(int row = 0; row < array.length; row++)
{
if (array[row][0].equals(prices[row][0]))
{
for(int i = 0; i<array[row].length; i++)
{
{Double d=Double.parseDouble(array[row][i]) * Double.parseDouble(prices[row][1]);
array[row][i] = d.toString();}
}
}
}
return array;
heres my new errors:
Exception in thread "main" java.lang.NumberFormatException: For input string: "Omaha"
at sun.misc.FloatingDecimal.readJavaFormatString(Unknown Source)
at java.lang.Double.parseDouble(Unknown Source)
at assign_1.DansUtilities.updateString(DansUtilities.java:429)
at assign_1.SalesReportGenerator.main(SalesReportGenerator.java:50)
NullPointerException can only be thrown if your array is null. Check in the code that is calling the method.
Other notes to improve your code:
you do not need a new array to store values. You can do it in existing array itself.
your inner for loop must be from 1 to the length of current row not the length of the array so it should be something like:
for(int i=1;i<array[row].length;i++)
And use index i instead of i+1 in loop content.
I suggest to create output of your strings, to see whether they are correctly read from files.
private static void outputString2D(String[][] s, String name) {
for ( int i = 0; i < s.length; i++) {
for ( int j = 0; j < s[i].length; j++ ) {
System.out.println(name + " contains at [" + i + "][" + j + "]:\t" + s[i][j]);
}
}
}
Example how I used it:
public static void main(String[] args) {
String[][] str = new String[2][3];
str[0][0] = new String("I am 0,0.");
str[0][1] = new String("I am 0,1.");
str[0][2] = new String("I am 0,2.");
str[1][0] = new String("I am 1,0.");
str[1][1] = new String("I am 1,1.");
str[1][2] = new String("I am 1,2.");
outputString2D(str, "str");
}
Example output:
str contains at [0][0]: I am 0,0.
str contains at [0][1]: I am 0,1.
str contains at [0][2]: I am 0,2.
str contains at [1][0]: I am 1,0.
str contains at [1][1]: I am 1,1.
str contains at [1][2]: I am 1,2.
Provide us the content of your two strings please.