Scanner is throwing NPE - java

My code is throwing an NPE‌ exception at line 27 and 32.
(names[i] = myScanner.nextLine();) +
(content[i] = myScanner.next();)
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Scanner;
public class Main {
static Scanner myScanner = new Scanner(System.in);
static int timesNames = 0;
static String[] names;
static String[] content = null;
public static void main(String[] args) {
System.out.println("How many things ? ");
timesNames = myScanner.nextInt();
for(int i = 0; i <= timesNames; i++ ){
int times = i + 1;
if(times <= timesNames ){
System.out.println("Thing Nr." + times);
System.out.println("");
System.out.println("Name of the thing: ");
names[i] = myScanner.nextLine();
System.out.println("");
System.out.println("Desciption : ");
content[i] = myScanner.next();
try {
File newTextFile = new File("P:/" + names[i] + ".txt");
FileWriter myFilewriter = new FileWriter(newTextFile);
myFilewriter.write(content[i]);
myFilewriter.close();
} catch (IOException iox) {
iox.printStackTrace();
}
}
}
}
}
What is causing this? Am I missing something?
I've searched about my problem but I didn't find anything helpful.

This would do it:
static String[] names;
static String[] content = null;
Both of those are initialized to null - one explicitly, one implicitly. You need to set some default size on them.
static String[] names = new String[timesNames];
static String[] content = new String[timesNames];

You haven't initialized names and content yet, so try:
names = new int[namesArraySize];
content = new String[contentArraySize];
where namesArraySize and contentArraySize should your sizes needed for your arrays (in your case it's probably timesNames).
You assigned content explicitly with null and names was set to null implicitly, so both are actually null when you try to access them by names[i] and content[i] (therefore the NPE).
If you don't know how many items there will be stored you should try a java.util.List.

Initialize the array after you know how many "things" there are:
public static void main(String[] args) {
System.out.println("How many things ? ");
timesNames = myScanner.nextInt();
names = new String[timesNames];
content = new String[timesNames];

You have many errors.
1. You didn't initialize the arrays
2.When you do you will probably give them the size of timeNames,which will give you a NPE inside your loop
To fix this you should change the conditions from i<=timeNmaes to i

Related

Array *not throwing out of bounds exception

I'm trying to learn about exception handling. I can't seem to get
String[] a = names(scnr); To throw an out of bounds exception when it goes beyond 3 elements. I know, most people hate the out of bounds error and I'm trying to make it happen and for the life of me I cannot figure out what I'm doing wrong. Been at it all day and googled all kinds of stuff. But I cannot seem to find exactly what I'm looking for. So I could use some help and perspective.
So I'm inputting a full string that I'm delimiting (trim and splitting) based on commas and spaces and then the pieces are being stored into an array (String []name), then passed to main to be output with String[] a. So it's not erroring when I go beyond 3 elements no matter how I do it. I can just not display anything beyond a[4]. But that's not really what I'm trying to do. Its my first java class so be gentle haha.
Any suggestions?
import java.util.*;
public class ReturnArrayExample1
{
public static void main(String args[])
{
Scanner scnr = new Scanner(System.in);
String[] a = names(scnr);
for (int i = 0; i < 3; i++)
{
System.out.println(a[i] + " in index[" + i + "].");
}
scnr.close();
}
public static String[] names(Scanner scnr)
{
String[] name = new String[3]; // initializing
boolean run = true;
do
{
try
{
System.out.println("Enter 3 names separated by commas ',':(Example: keith, mark, mike)");
String rawData = scnr.nextLine();
if(rawData.isEmpty())
{
System.err.println("Nothing was entered!");
throw new Exception();
}
else
{
name = rawData.trim().split("[\\s,]+");
run = false;
}
}
catch(ArrayIndexOutOfBoundsException e)
{
System.err.println("Input is out of bounds!\nUnsuccessful!");
}
catch(Exception e)
{
System.err.println("Invalid entry!\nUnsuccessful!");
}
}
while(run == true);
System.out.println("Successful!");
scnr.close();
return name;
}
}
If I understand you correctly, you want to throw an ArrayOutOfBoundsException if the names array does not contain exactly 3 elements. The following code is the same as the one you wrote with an if-statement to do just that.
import java.util.*;
public class ReturnArrayExample1
{
public static void main(String args[])
{
Scanner scnr = new Scanner(System.in);
String[] a = names(scnr);
for (int i = 0; i < 3; i++)
{
System.out.println(a[i] + " in index[" + i + "].");
}
scnr.close();
}
public static String[] names(Scanner scnr)
{
String[] name = new String[3]; // initializing
boolean run = true;
do
{
try
{
System.out.println("Enter 3 names separated by commas ',':(Example: keith, mark, mike)");
String rawData = scnr.nextLine();
if(rawData.isEmpty())
{
System.err.println("Nothing was entered!");
throw new Exception();
}
else
{
name = rawData.trim().split("[\\s,]+");
if (name.length != 3) {
throw new ArrayIndexOutOfBoundsException();
}
run = false;
}
}
catch(ArrayIndexOutOfBoundsException e)
{
System.err.println("Input is out of bounds!\nUnsuccessful!");
}
catch(Exception e)
{
System.err.println("Invalid entry!\nUnsuccessful!");
}
}
while(run == true);
System.out.println("Successful!");
scnr.close();
return name;
}
}
If you want java to throw an ArrayIndexOutOfBoundException you have to preserve the created names instance and let java copy the array into your names array:
String[] names=new String[3];
String[] rawElements=rawData.trim().split("[\\s,]+");
System.arraycopy(rawElements, 0, names, 0, rawElements.length);
output:
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException
at java.lang.System.arraycopy(Native Method)
at stackoverflow.OutOfBound.main(OutOfBound.java:8)
As far as I understand, you are expecting an exception (ArrayIndexOutOfBoundsException) to the thrown at line
name = rawData.trim().split("[\\s,]+");
with an argument that the size of array (name) is fixed to 3, and when if the input is beyond 3 then the exception must be thrown; which is not the case.
The reason is in the way assignment happens in java. When you declare String[] name = new String[3];, then an object is created in java heap and its reference is assigned to variable name which is in stack memory.
And when this line name = rawData.trim().split("[\\s,]+"); gets executed then a new array object is created in heap and the variable name starts pointing to the newly created array object on heap. Note: the old object will get available for garbage collection after some time.
This eventually changes the length of the array variable (name) and you do not get any ArrayIndexOutOfBoundsException.
You can understand this more clearly by printing the object on console, like System.out.println(name); after its initialisation and post its assignment.
I will also suggest you to refer this link (https://books.trinket.io/thinkjava2/chapter7.html#elements) to understand how array are created, initialised and copied etc..
Code with system.out commands (for understanding)
import java.util.Scanner;
public class ReturnArrayExample1 {
public static void main(String args[]) {
Scanner scnr = new Scanner(System.in);
String[] a = names(scnr);
System.out.println("Variable (a) is referring to > " + a);
for (int i = 0; i < 3; i++) {
System.out.println(a[i] + " in index[" + i + "].");
}
scnr.close();
}
public static String[] names(Scanner scnr) {
String[] name = new String[3]; // initializing
System.out.println("Variable (name) is referring to > " + name);
boolean run = true;
do {
try {
System.out.println("Enter 3 names separated by commas ',':(Example: keith, mark, mike)");
String rawData = scnr.nextLine();
if (rawData.isEmpty()) {
System.err.println("Nothing was entered!");
throw new Exception();
} else {
name = rawData.trim().split("[\\s,]+");
System.out.println("Now Variable (name) is referring to > " + name);
run = false;
}
} catch (ArrayIndexOutOfBoundsException e) {
System.err.println("Input is out of bounds!\nUnsuccessful!");
} catch (Exception e) {
System.err.println("Invalid entry!\nUnsuccessful!");
}
} while (run == true);
System.out.println("Successful!");
scnr.close();
return name;
}
}
I you want to throw exception when input is more than 3 then there are many ways to do it. One suggestion from #mohamedmoselhy.com is also decent.

read lines from external file and store elements in array

I am new here so please show some patience. I am trying to read the data from an external file and store the info in 2 arrays.
The file looks like this:
0069 723.50
0085 1500.00
0091 8237.31
I am using 2 scanners to read the input and I think they work ok because when I try to print, the result looks ok.
My first problem is that I am able to read the first numbers on the list using nextInt(), but cannot use nextDouble() for the double ones as I get the "java.util.InputMismatchException" message. For that reason I read it as a String. The part with the other two scanners is supposed to do what the first parts should do, for a different input file, but the problem is the same.
My next and biggest problem, until now, is that am not able to store the values from the two columns in two distinct arrays. I have tried several ways (all commented) but all fail. Please help and thanks.
Here is my code:
import ui.UserInterfaceFactory;
import java.io.PrintStream;
import java.util.Arrays;
import java.util.Scanner;
import ui.UIAuxiliaryMethods;
public class Bank {
static final int MAX_NUMBER_OF_ACCOUNTS = 50;
PrintStream out;
Bank(){
UserInterfaceFactory.enableLowResolution(true);
out = new PrintStream(System.out);
}
void readFiles(){
Scanner balanceFile = UIAuxiliaryMethods.askUserForInput().getScanner();
while(balanceFile.hasNextLine()){
String balance_Line = balanceFile.nextLine();
Scanner accountsFile = new Scanner(balance_Line);
int account = accountsFile.nextInt(); //works
out.printf("%04d ",account);
/*int [] accounts_array = new int [MAX_NUMBER_OF_ACCOUNTS]; //does not store the values properly
int account = accountsFile.nextInt();
for(int j=0; j < accounts_array.length; j++){
accounts_array[j] = account;
}*/
/*int [] accounts_array = new int [MAX_NUMBER_OF_ACCOUNTS]; //java.util.InputMismatchException
for(int j=0; j < accounts_array.length; j++){
accounts_array[j] = accountsFile.nextInt();
//out.printf("%04d \n",accounts_array[j]);
}*/
String balance = accountsFile.nextLine(); //problem declaring balance as a double
out.printf("%s\n",balance);
/*String [] balance_array = new String [MAX_NUMBER_OF_ACCOUNTS]; //java.util.NoSuchElementException
for(int j=0; j < balance_array.length; j++){
accountsFile.useDelimiter(" ");
balance_array[j] = accountsFile.next();
//out.printf("%04d \n",accounts_array[j]);
}*/
}
Scanner mutationsFile = UIAuxiliaryMethods.askUserForInput().getScanner();
while(mutationsFile.hasNext()){
String mutation_Line = mutationsFile.nextLine();
Scanner mutatedAccountsFile = new Scanner(mutation_Line);
int mutated_account = mutatedAccountsFile.nextInt();
out.printf("%04d ",mutated_account);
int action = mutatedAccountsFile.nextInt(); //deposit or withdrawal
/*if (action == 1){
}else{
}*/
out.printf(" %d ",action);
/*Double amount = mutatedAccountsFile.nextDouble();
out.printf(" %5.2f ",amount);*/
String amount = mutatedAccountsFile.nextLine();
out.printf("%s\n",amount);
}
}
void start(){
new Bank();readFiles();
}
public static void main(String[] args) {
new Bank().start();
}
}
The InputMismatchException occurs because you try to read a double using the nextInt() function. To solve this issue, you can first read the tokens as Strings using the next() function and convert them appropriately.
while(mutationsFile.hasNext()){
mutation_Line = mutationsFile.next();
if(mutation_Line.indexOf(".") == -1)
//token is int
else
//token is double
}
Since you already know what the contents of the two columns are, you can store the integers and doubles in two lists and then, if you want, get them into an array.
List<Integer> intList = new ArrayList<Integer>();
List<Double> doubleList = new ArrayList<Double>();
Now replace the if statements in the first snippet with this:
if(mutation_Line.indexOf(".") == -1)
intList.add(new Integer(Integer.parseInt(mutation_Line)));
else
doubleList.add(new Double(Double.parseDouble(mutation_Line)));
In the end, you can get them into arrays:
Object[] intArr = intList.toArray(),
doubleArr = doubleList.toArray();
//display the contents:
for(int i=0; i<intArr.length; i++)
out.printf("%04d\t%.2f\n", Integer.parseInt(intArr[i].toString()),
Double.parseDouble(doubleArr[i].toString()));
OUTPUT:
0069 723.50
0085 1500.00
0091 8237.31
First off, you don't need to use 2 scanners. The Scanner object is simply reading your file, one scanner is plenty to accomplish the task of reading a file.
If you're trying to read the integers/doubles from file and are having trouble with nextInt() and nextDouble(), consider a different approach to parsing (e.g. parse the line into a string, split the line into 2 parts based on a space character, then trim both resulting strings and convert to respective integers/doubles).
Now back to the Scanner parsing the two values, remember first that when you use a next() or nextInt(), etc. those methods consume the next respective token. So parsing a line as a string from the file into another Scanner object is redundant and unnecessary in this case.
If you know your max number of accounts, and it's simply 50, then go ahead an allocate that prior to the while loop.
Here's an alternative approach with the code you posted.
public class App {
static int MAX_NUMBER_OF_ACCOUNTS = 50;
static PrintStream out;
static void readFiles() {
Scanner balanceFile = null;
try {
balanceFile = new Scanner(new File("C:\\Users\\Nick\\Desktop\\test.txt"));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
if (balanceFile == null)
return;
int [] accounts_array = new int [MAX_NUMBER_OF_ACCOUNTS];
double [] balance_array = new double [MAX_NUMBER_OF_ACCOUNTS];
int currentIndex = 0;
while (balanceFile.hasNextLine()) {
int account = balanceFile.nextInt();
double balance = balanceFile.nextDouble();
System.out.print("acc = " + account + " ");
System.out.println("bal = " + balance);
//out.printf("%04d ", account);
accounts_array[currentIndex] = account;
//out.printf("%s\n", balance);
balance_array[currentIndex] = balance;
currentIndex++;
}
balanceFile.close();
}
static void start() {
readFiles();
}
public static void main(String[] args) {
start();
}
}
Please note the excessive use of static could also be avoided in the future, but for the sake of the example it spread like the plague.
As you can see in the logic leading up to the while loop, the scanner object is made from a file I copied your example data into a file on my desktop. The arrays are allocated prior to the while loop (note: see #progy_rock and their use of ArrayList's - may help improve your code in the long run). And finally, note the index count to move the position along in the array to which you are inserting your lines to.

Fix the array type and method error in my java classes, really lost at how to fix the error

I have the following error when I run my parser program,
Error: Main method not found in class TfIdfMain, please define the main method as:
public static void main(String[] args)
or a JavaFX application class must extend javafx.application.Application
Also in my main method, there is a error like this, but I already created the parserfile error in parser class,
Multiple markers at this line
- Default constructor cannot handle exception type IOException thrown by implicit super constructor. Must define an explicit
constructor
- Default constructor cannot handle exception type FileNotFoundException thrown by implicit super constructor. Must define an
explicit constructor
Also in my parser class, there is an error around the array list line, it says array cannot be resolved, how should I fix this? Create a new variable.
Here are my two main classes involved the errors:
import java.io.FileNotFoundException;
import java.io.IOException;
public class TfIdfMain {
}
// public static void main(String args[]) throws FileNotFoundException, IOException {
// DocumentParser dp = new DocumentParser();
// dp.parseFiles("C:\\Users\\Sarah\\Documents");
// dp.getCosineMatrix();
// }
}
}
My document parser class:
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
public class DocumentParser {
private void doSomething(){
String text = "Professor, engineering, data, mining, research";
StringTokenizer str = new StringTokenizer(text);
String word[] = new String[10];
String unique[] = new String[10];
String x;
int count = -1;
while (str.hasMoreTokens()) {
count++;
x = str.nextToken();
if (f.getName().endsWith(".txt")) {
in = new BufferedReader(new FileReader(f));
StringBuilder sb = new StringBuilder();
String s = null;
while ((s = in.readLine()) != null) {
sb.append(s);
}
String[] tokenizedTerms = sb.toString().replaceAll("[\\W&&[^\\s]]", "").split("\\W+"); //to get individual terms
for (String term : tokenizedTerms) {
if (!allTerms.contains(term)) {
allTerms.add(term);
}
}
termsDocsArray.add(tokenizedTerms);
}
}
}
public void tfIdfCalculator() {
double tf;
double idf;
double tfidf;
for (String[] docTermsArray : termsDocsArray) {
double[] tfidfvectors = new double[allTerms.size()];
int count = 0;
for (String terms : allTerms) {
tf = new TfIdf().getTf(docTermsArray, terms);
idf = new TfIdf().idfCalculation(termsDocsArray, terms);
tfidf = tf * idf;
tfidfvectors[count] = tfidf;
count++;
}
tfidfDocsVector.add(tfidfvectors);
}
}
public void getCosineMatrix() {
for (int i = 0; i < tfidfDocsVector.size(); i++) {
for (int j = 0; j < tfidfDocsVector.size(); j++) {
System.out.println("between " + i + " and " + j + " = "
+ new CosineSimilarity().getCosine
(
tfidfDocsVector.get(i),
tfidfDocsVector.get(j)
)
);
}
}
}
}
read your error-message and then check your code:
Error: Main method not found in class TfIdfMain, please define the main method as:
public static void main(String[] args)
what could be the problem? the main-method was not found. In your code it is commented out.
And in your TfIdfMain-class:
at least your for-loop has to be in a method / constructor.
Do something like
public class TfIdfMain
public TfIdfMain(){
for(String file : files) {
DocumentParser dp = new DocumentParser();
dp.parseFiles(file);
dp.getCosineMatrix();
}
}
}
your main method is commented out, that is why it isn't found by the compiler.
The for loop isn't inside a method and only in the class body. This is wrong in java.
The error messages from the compiler tell you exactly what to do, you have to provide an special constructor which can handle the exceptions.

Bubble sorting arraylis is not working

I'm trying to bubble sort car make and year, where I would have the car year sorted and if two car makes are in the same year, then they are sorted alphabetically. My program works up to the point where I call BubbleSorted(). It's giving me an error java.lang.IndexOutOfBoundsException: Index: 0, Size: 0 and I don't know why. My program seems to be correct. Below is my program. I have 3 classes(main, bubblesortCars, GetCarInfo).
import java.util.ArrayList;
import java.util.Scanner;
import java.util.StringTokenizer;
import java.io.BufferedReader;
import java.io.FileReader;
public class TheMain {
public static void main(String[] args) {
Scanner keyboard=new Scanner(System.in);
int choice;
boolean done = false;
try{
String filename1 = "Demo.txt";
FileReader inputFile = new FileReader(filename1);
//Instantiate the BufferedReader Class
BufferedReader bufferReader = new BufferedReader(inputFile);
ArrayList<GetCarInfo> CarList = new ArrayList();
//Variable to hold the one line data
String line;
StringTokenizer st;
int i=0;
// Read file line by line and print on the console
while ((line = bufferReader.readLine()) != null) {
st = new StringTokenizer(line, "\t");
st.nextToken();
st.nextToken();
String getMake = st.nextToken();
st.nextToken();
int getYear = Integer.parseInt(st.nextToken());
GetCarInfo temp;
temp = new GetCarInfo(getMake, getYear);
CarList.add(temp);
}
bufferReader.close();
BubbleSortCars Sorted = new BubbleSortCars();
Sorted.bubblesorted(CarList, 0, CarList.size());
}
catch (Exception e)
{
e.printStackTrace();
}
}
}
import java.util.ArrayList;
public class BubbleSortCars {
ArrayList <GetCarInfo> temp= new ArrayList();
public void bubblesorted(ArrayList <GetCarInfo> grabber, int began, int end){
for(int i =0; i<end-began-1; i++){
for(int j=began; j<(end-i-1); j++){
if(grabber.get(j).year > grabber.get(j+1).year){
temp.set(j, grabber.get(j));
grabber.set(j,grabber.get(j+1));
grabber.set(j+1, temp.get(j));
System.out.println("Success");
}
else if(grabber.get(j).year==grabber.get(j+1).year){
if((grabber.get(j).make).compareTo(grabber.get(j+1).make)>0){
temp.set(j, grabber.get(j));
grabber.set(j, grabber.get(j+1));
grabber.set(j+1, temp.get(j));
System.out.println("Success");
}
}
}
}
}
}
public class GetCarInfo {
int year;
String make;
public GetCarInfo(String newmake, int newyear){
make = newmake;
year = newyear;
}
}
Reason you get IndeOutOfBoundException is due to this line:
temp.set(j, grabber.get(j));
and your definition of arrayList.
ArrayList<GetCarInfo> temp = new ArrayList();
Here you are defining temp as arrayList without any element and you are trying to set an element at 0th location which is not defined. See this for your reference http://docs.oracle.com/javase/7/docs/api/java/util/ArrayList.html#set%28int,%20E%29
When you define temp as above it created with size 0 and jdk does check internally if index that you are trying to access is less than size then only it will allow you to access/set content.
So one way to avoid this, you define your temp arrayList in your method like:
ArrayList<GetCarInfo> temp = new ArrayList(grabber);
Or you could use grabber arrayList to do the sorting without any other data structure.
The problem is with the ArrayList temp. Please refer the Oracle documentation for the set method.
Here you don't need an ArrayList. User a simple GetCarInfo object as temp variable.

How do I have a program create its own variables with Java?

I would like to start off by saying that if this is common knowledge, please forgive me and have patience. I am somewhat new to Java.
I am trying to write a program that will store many values of variables in a sort of buffer. I was wondering if there was a way to have the program "create" its own variables, and assign them to values.
Here is an Example of what I am trying to avoid:
package test;
import java.util.Scanner;
public class Main {
public static void main(String args[]) {
int inputCacheNumber = 0;
//Text File:
String userInputCache1 = null;
String userInputCache2 = null;
String userInputCache3 = null;
String userInputCache4 = null;
//Program
while (true) {
Scanner scan = new Scanner(System.in);
System.out.println("User Input: ");
String userInput;
userInput = scan.nextLine();
// This would be in the text file
if (inputCacheNumber == 0) {
userInputCache1 = userInput;
inputCacheNumber++;
System.out.println(userInputCache1);
} else if (inputCacheNumber == 1) {
userInputCache2 = userInput;
inputCacheNumber++;
} else if (inputCacheNumber == 2) {
userInputCache3 = userInput;
inputCacheNumber++;
} else if (inputCacheNumber == 3) {
userInputCache4 = userInput;
inputCacheNumber++;
}
// And so on
}
}
}
So just to try to summarize, I would like to know if there is a way for a program to set an unlimited number of user input values to String values. I am wondering if there is a way I can avoid predefining all the variables it may need.
Thanks for reading, and your patience and help!
~Rane
You can use Array List data structure.
The ArrayList class extends AbstractList and implements the List
interface. ArrayList supports dynamic arrays that can grow as needed.
For example:
List<String> userInputCache = new ArrayList<>();
and when you want to add each input into your array like
if (inputCacheNumber == 0) {
userInputCache.add(userInput); // <----- here
inputCacheNumber++;
}
If you want to traverse your array list you can do as follows:
for (int i = 0; i < userInputCache.size(); i++) {
System.out.println(" your user input is " + userInputCache.get(i));
}
or you can use enhanced for loop
for(String st : userInputCache) {
System.out.println("Your user input is " + st);
}
Note: it is better to put your Scanner in your try catch block with resource so you will not be worried if it is close or not at the end.
For example:
try(Scanner input = new Scanner(System.in)) {
/*
**whatever code you have you put here**
Good point for MadProgrammer:
Just beware of it, that's all. A lot of people have multiple stages in their
programs which may require them to create a new Scanner AFTER the try-block
*/
} catch(Exception e) {
}
For more info on ArrayList
http://www.tutorialspoint.com/java/java_arraylist_class.htm

Categories