Error in taking input from file using scanner class in java - java

I want to take input from a file using the scanner class in Java. I want to read two coordinates of different cities from the file and then store them in an ArrayList of type City objects.
The input file format is as follows:
NAME : att48
COMMENT : 48 capitals of the US (Padberg/Rinaldi)
TYPE : TSP
DIMENSION : 5
EDGE_WEIGHT_TYPE : ATT
NODE_COORD_SECTION
1 6734 1453
2 2233 10
3 5530 1424
4 401 841
5 3082 1644
My sample code fragment is as follows: TourManager is a class containing an ArrayList of City objects. I haven't shown it here. City class contains every details (x,y coordinates) of a city.
try
{
Scanner in = new Scanner(new File("att48.tsp"));
String line = "";
int n;
//three comment lines
in.nextLine();
in.nextLine();
in.nextLine();
//get n
line = in.nextLine();
line = line.substring(11).trim();
n = Integer.parseInt(line);
City[] city= new City[n];
for (int i = 0; i < n; i++) {
city[i].x=0;
city[i].y=0;
}
//two comment lines
in.nextLine();
in.nextLine();
for (int i = 0; i < n; i++)
{
in.nextInt();
city[i].x = in.nextInt();
city[i].y = in.nextInt();
TourManager.addCity(city[i]);
}
}
catch (Exception e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
But I am getting a NullPointerException in the line.
city[i].x = in.nextInt();
Although I have initialized it by 0 previously, the code throws the NullPointerException.
For clarity, City class is as follows:
public class City {
int x;
int y;
// Constructs a city at chosen x, y location
public City(int x, int y){
this.x = x;
this.y = y;
}
}
Is there a problem in the code?

You are getting error because after doing :
City[] city= new City[n];
You have not allocated memory to individual city[i] elements.
You have to do something like this, but for this you need to add a default constructor to your city class as you are assigning x and y afterwards:
for (i=0;i <n ;i++){
city[i]= new City();
}
Add the following constructor in your City class:
public City(){
}
or I would suggest you to revise your City class:
public class City {
private int x;
private int y;
// Constructs a city at chosen x, y location
public City(int x, int y) {
this.setX(x);
this.setY(y);
}
public City() {
}
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
}

Related

Read alternating data types from file

I'm trying to read coordinates from a file into an array.
Every coordinate has an id, an x-value and a y-value.
The file is in the following format: id position.x position.y
Example:
292961234 1376.42 618.056
29535583 3525.73 530.522
256351971 836.003 3563.33
20992560 4179.74 3074.27
Note: There are 4 lines containing a total of 4 coordinates.
I created the class Node and its constructor expects (int id, double x, double y).
And this is the class NodeList which is supposed to have an array attribute that saves the Nodes:
package .....;
import java.io.File;
import java.util.Iterator;
import java.util.Locale;
import java.util.Scanner;
public class NodeList implements Iterable<Node> {
private Node[] nodes = getNodes();
#Override
public Iterator<Node> iterator() {
return null;
}
public Node[] getNodes() {
Node[] result;
File f;
Scanner scanner;
try {
f = new File("nodes.txt");
Scanner s = new Scanner(f);
int ctr = 0;
while (s.hasNextLine()) {
ctr++;
s.nextLine();
}
result = new Node[ctr];
}
catch (Exception e) {
return null;
}
try {
scanner = new Scanner(f);
}
catch (Exception e) {
return null;
}
Locale.setDefault(new Locale("C"));
for(int i = 0; i < result.length; i++) {
int id = scanner.nextInt();
double x = scanner.nextDouble();
double y = scanner.nextDouble();
result[i] = new Node(id,x,y);
}
return result;
}
public static void main(String[] args) {
NodeList nl = new NodeList();
}
}
The Node class:
package ...;
public class Node {
private int id;
private double x;
private double y;
public Node(int id, double x, double y){
this.id = id;
this.x = x;
this.y = y;
}
public int getId(){
return id;
}
public double getX(){
return x;
}
public double getY(){
return y;
}
}
When the method containing the shown code is called, I get the following
Exception:
Exception in thread "main" java.util.InputMismatchException
at java.base/java.util.Scanner.throwFor(Scanner.java:939)
at java.base/java.util.Scanner.next(Scanner.java:1594)
at java.base/java.util.Scanner.nextDouble(Scanner.java:2564)
at ......NodeList.getNodes(NodeList.java:40)
at ......NodeList.<init>(NodeList.java:9)
at ......NodeList.main(NodeList.java:47)
Process finished with exit code 1
Link to the file containing the nodes: https://pastebin.com/zhzp3DTi
It might be that it is using wrong locale.
I don't think "C" is a valid locale, it should be a language code.
You can try to use
scanner.useLocale(Locale.ROOT);
This is working on my machine:
public static void main(String[] args) {
// TODO code application logic here
String s = "292961234 1376.42 618.056\n" +
"29535583 3525.73 530.522\n" +
"256351971 836.003 3563.33\n" +
"20992560 4179.74 3074.27";
Scanner scanner = new Scanner(s);
scanner.useLocale(Locale.ROOT);
for(int i = 0; i < 4; i++) {
int id = scanner.nextInt();
double x = scanner.nextDouble();
double y = scanner.nextDouble();
System.out.println(id+" "+x+" "+y);
}
}

How can I create a Table of string indexs for rows and columns and boolean values for cells?

I need a java program that can solve the following issues:
1- It has a data structure (DS) to represent the following data where rows and columns are indexed by Strings and cells values are booleans.
So that, to access row (i), I can simply say DS["Yi"] and to access a particular cell (j) in row (i) I can say DS["Yi","Xj"]
2- The column indexs {"X1", "X2", "X3", ..., "Xn"} has to be populated from a class fields. For example consides the following class:
public class Test {
private String X1;
private String X2;
private String X3;
private String X4;
private String X5;
}
For this class, my table's column is going to be {"X1", "X2", "X3", "X4", "X5"}, and if I later update class Test to include one more field, let's say "X6", then DS has to automatically include this new field.
3- Finally, I want to save these data into a file {TXT, XML, or JSON} so that every time the code runs, it can read the values from the file.
I think the easiest thing to do might be to have some convention whereby you can internally convert known row and column labels into numerical indices. Then, you could just use a plain 2D boolean array.
If you can't do this, then one option would be to use a map of maps, something like this:
Map<String, Map<String, Boolean>> grid = new HashMap<>();
// populate first row
grid.put("Y1", new HashMap<>());
grid.get("Y1").put("X1", true);
grid.get("Y1").put("X2", true);
grid.get("Y1").put("X3", false);
// ... other columns
grid.get("Y1").put("Xn", true);
Give it a try with this approach.
N.B.: this code is not tested. Here I've used both int index search on array because I will assume the the list for example "x1", "x2", "x3" is not necessarily to be arranged(probably you can try with Map)
public class SS {
public static void main(String[] args) {
//Used for indexing
List<String> listX = Arrays.asList("x1", "x2", "x3");
List<String> listY = Arrays.asList("y1", "y2", "y3");
//Used to fetch boolean value which is indexed arr[x][y] with the value defined in the class YourClass
YourClass[][] arr = new YourClass[listX.size()][listY.size()];
int i=0;
for (String y : listY) {
int j=0;
for (String x : listX) {
//Fill the array
arr[i][j] = new YourClass(new Random().nextInt(1), x, y);
j++;
}
i++;
}
//To get DS["x2", "y3"]
DS ds = new DS("x2", "y3");
i=0;
for (String y : listY) {
if(ds.getY().equals(y))
{
int j=0;
for (String x : listX) {
if(ds.getX().equals(x))
System.out.println(arr[i][j].toString());
j++;
}
}
i++;
}
}
}
//class to maintain index positions
class YourClass{
int a;
String x;
String y;
public YourClass(int a, String x, String y) {
this.a = a;
this.x = x;
this.y = y;
}
#Override
public String toString() {
return "YourClass{" +
"a=" + a +
", x='" + x + '\'' +
", y='" + y + '\'' +
'}';
}
public int getA() {
return a;
}
public void setA(int a) {
this.a = a;
}
public String getX() {
return x;
}
public void setX(String x) {
this.x = x;
}
public String getY() {
return y;
}
public void setY(String y) {
this.y = y;
}
}
//class used to search the element
class DS {
String x;
String y;
public String getX() {
return x;
}
public void setX(String x) {
this.x = x;
}
public String getY() {
return y;
}
public void setY(String y) {
this.y = y;
}
public DS(String x, String y) {
this.x = x;
this.y = y;
}
}

How to load/create a level/room from a text file in java?

Basically each room has a size of 10 by 10, the "W" represents the Walls, and the blank spaces -" " represent the Floor, and the numbers are Doors.I figured the best way to create the room is to create a method that receives a file and reads it and put its "information" into a String[10][10], and then create another method(or just do it in my Main) that receives the String[10][10] created and creates the room(adds the images to the room), but i am having some difficulties reading the file so if you guys could help me with that part i would be thankful.
Here is the type of text files from which i want to create my room:
WWWW0WWWWW
W W
W W
W W
W W
W WW
W WW
W WW
W W1
WWWWWWWWWW
Here are the Door, Wall and Floor classes:
public class Door implements ImageTile {
private Position position;
public Door(Position position) {
this.position = position;
}
#Override
public String getName() {
return "Door";
}
#Override
public Position getPosition() {
return position;
}
}
public class Floor implements ImageTile {
private Position position;
public Floor(Position position) {
this.position = position;
}
#Override
public String getName() {
return "Floor";
}
#Override
public Position getPosition() {
return position;
}
}
public class Wall implements ImageTile {
private Position position;
public Wall(Position position) {
this.position = position;
}
#Override
public String getName() {
return "Wall";
}
#Override
public Position getPosition() {
return position;
}
}
And this is my method for adding images to my frame:
public void newImages(final List<ImageTile> newImages) {
if (newImages == null)
return;
if (newImages.size() == 0)
return;
for (ImageTile i : newImages) {
if (!imageDB.containsKey(i.getName())) {
throw new IllegalArgumentException("No such image in DB " + i.getName());
}
}
images.addAll(newImages);
frame.repaint();
}
If you guys could help me i would appreciate it very much, thanks guys.Her is what i have now:
public class Room {
private String[][]room;
public Room(){
room = new String[10][10]; }
public static Room fromFile(File file){
if(file.exists()){
Scanner sc = null;
Room room = new Room();
try {
sc = new Scanner(file);
while(sc.hasNextLine()){
if(sc.nextLine().startsWith("#"))
sc.nextLine();
else{
String[] s0 = sc.nextLine().split("");
//Here is where my trouble is, i dont know how to add the content of this String s0 to the String s
if(s0.length==10){
for(int x = 0; x < 10; x++){
for(int y = 0; y < 10; y++){
String[x][y] s= String[x] s0;
}
}
} catch (FileNotFoundException e) {
System.out.println("Ficheiro "+file.getAbsolutePath()+
" não existe. "); }
finally{
if(sc!=null)sc.close();
}
}
else
System.out.println("Ficheiro "+file.getAbsolutePath()+
" não existe. ");
return null;
}
Each call to sc.nextLine() is reading another line from your file. You need to save the line into a temporary variable, and then refer to that temporary.
Maintain a counter of lines you've processed, so you can fill in the appropriate line in your s[][] matrix.
You only need to allocate storage for the 10 rows, since splitting the line you read in will result in an array of strings (the columns in one row) being allocated for you.
int row = 0;
String[][] s = new String[10][];
while(sc.hasNextLine() && i < 10) {
String line = sc.nextLine();
if( !line.startsWith("#")) {
String[] s0 = sc.line.split("");
s[row] = s0;
row++;
}
}
BTW, Use String[][] is overkill; since each string will only hold one character. Perhaps you could consider using char[][]. And line.toCharArray() would split the line into a char[] for you.
EDIT: (Due to edit of your question's code)
Instead of:
if(s0.length==10){
for(int x = 0; x < 10; x++){
for(int y = 0; y < 10; y++){
String[x][y] s= String[x] s0;
}
}
}
you want:
if(s0.length==10){
for(int y = 0; y < 10; y++){
s[row][y] = s0[y];
}
row++;
}
With row being the row counter in my above code.

I'm trying to store and manage ordered pairs in the form (x,y). As in coordinates in an array using an inner class [duplicate]

This question already has answers here:
What is a debugger and how can it help me diagnose problems?
(2 answers)
Closed 7 years ago.
I want to be able to store and manage ordered pairs of the
form: (x, y). To solve this problem I created two classes: EuclideanSpace and Point. This is a homework assignment and so it is set up with these specific methods and the class EuclideanSpace and the inner class Point. I thought I had it almost figured out but when I run it it prints out '0' for the x and the y values after the first entry. For every entry after that it prints 'null'.
import java.util.Scanner;
public class EuclideanSpace {
Point point[];
Scanner scanner = new Scanner(System.in);
public EuclideanSpace() {
point = new Point[10];
}// End constructor
// Adds points to the array
public boolean addPoint(int x, int y) {
for (int i = 0; i < 10; i++) {
if (point[i] == null) {
point[i] = new Point();
}// End if
return true;
}// End for
return false;
}// End addPoint
// Prints a point in a given index in the point array
public void printPoint(int i) {
System.out.println(point[i]);
}
// Inner class
public static class Point {
private int x;
private int y;
public void Point(int x, int y) {
this.x = x;
this.y = y;
}// End Point method
public String toString() {
return "X = " + x + "Y = " + y;
}// End toString
}// End inner Class
}// End
Driver class:
import java.awt.Point;
import java.util.Scanner;
public class ICDriver {
static Scanner scanner = new Scanner(System.in);
// New object from the class EuclideanSpace
static EuclideanSpace es = new EuclideanSpace();
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
System.out.println("Add point x coordinate? ");
int pointX = scanner.nextInt();
System.out.println("Add point y coordinate? ");
int pointY = scanner.nextInt();
es.addPoint(pointX, pointY);
es.printPoint(i);
} // End for
}// End main
}// End
// Correct your addPoint method
public boolean addPoint(int x, int y) {
for (int i = 0; i < 10; i++) {
if (point[i] == null) {
point[i] = new Point(x,y);
return true;
}// End if
}// End for
return false;
}// End addPoint
//Remove void from your constructor
public Point(int x, int y) {
this.x = x;
this.y = y;
}

Exception in thread "main" java.util.InputMismatchException "Graph"

I am a beginner in Java and I get this java.util.InputMismatchException for the code I have written it below. The error is:
Exception in thread "main" java.util.InputMismatchException
at java.util.Scanner.throwFor(Scanner.java:864)
at java.util.Scanner.next(Scanner.java:1485)
at java.util.Scanner.nextInt(Scanner.java:2117)
at java.util.Scanner.nextInt(Scanner.java:2076)
at Graph.main(Graph.java:103)
Once debugging it gives the error when it is going to execute int size = scan.nextInt(); line in main methor. I would appreciate if anyone can help me with this.
import java.io.*;
enter code here`import java.util.*;
import java.util.Random;
public class Graph {
private int maxSize;
private Vertex[] nodes; // array of nodes
private int[][] mat; // adjacency matrix
private int N;
public Graph(int maxSize) {
this.maxSize = maxSize;
nodes = new Vertex[maxSize];
mat = new int[maxSize][maxSize];
for(int i=0; i<maxSize;i++)
for(int j=0; j<maxSize;j++) mat[i][j]=0;
}
public void addVertex(int x, int y) {
if (N >= maxSize) {
System.out.println("Graph full");
return;}
nodes[N++] = new Vertex(x , y);
}
public void addEdge(int v1, int v2) {
mat[v1][v2] = 1;
mat[v2][v1] = 1;
}
//public static void main(String args[]) throws IOException
public void readFile() throws IOException
{
int xcoord;
int ycoord;
Scanner scan = new Scanner("vertex.txt");
int size = scan.nextInt();
int count = 0;
while (scan.hasNext() && count<size) {
scan.nextLine();
nodes[count].setX(scan.nextInt());
nodes[count].setY(scan.nextInt());
count++;
}
//Reads the edges file
Scanner scanEdge = new Scanner("edges.txt");
size = scanEdge.nextInt();
count = 0;
int weight;
//fill out the adjacency matrix
while (scanEdge.hasNext() && count<size) {
scanEdge.nextLine();
xcoord = scanEdge.nextInt(); // "from" node
ycoord = scanEdge.nextInt(); // "to" node
mat[xcoord][ycoord]=scanEdge.nextInt(); //weigth of the link
mat[ycoord][xcoord] = mat[xcoord][ycoord]; //Symmetric matrix
count++;
scanEdge.nextLine();
}
return;
}
public static void main(String args[]){
EasyIn easy = new EasyIn();
// Prints menu
System.out.println();
System.out.println("Welcome to Maze Genrator App");
System.out.println("=============================");
System.out.println("Menu");
System.out.println("====");
System.out.println("1- Read Graph from File");
System.out.println("2- Generate a Graph using a Grid with Random weigths");
System.out.println("3- Compute the Minimum Spanning Tree");
System.out.println("0- Exit");
int command = -1;
while (command != 0) {
if (command > 0) {String pause = easy.readString();} //Creates a pause
System.out.println();
command = easy.readInt(); //Takes command
switch (command){
case 1:
//Reads the vertices file.
Scanner scan = new Scanner("vertex.txt");
int size = scan.nextInt();
//Reads the vertices file
Graph myGraph = new Graph(size);
//String fileName = easy.readString();
try{
myGraph.readFile();
}
catch(IOException e){
e.printStackTrace();
}
System.out.println("List of edges + weigths");
break;
case 0: //Exit command
break;
default:
System.out.println("Selection Invalid!- Try Again");
}
}
System.out.println("Goodbye!");
}
}
public class Vertex {
// The vertex coordinates
private int x;//label e.g. A,B
private int y;//label e.g. A,B
public boolean visited; //Wether the node is visited or not
public Vertex (int x, int y) {
this.x = x;
this.y = y;
visited = false;
}
//display x,y coordinates of the graph
public void display() {
System.out.println(x + " " + y);
}
//set x coordinate
public void setX(int x){
this.x = x;
}
//set y coordinate
public void setY(int y){
this.y = y;
}
}
Once debugging it gives the error when it is going to execute "int
size = scan.nextInt();" line
It means that the next token isn't an integer.
You may want to call and check the return value of scan.hasNextInt(), to prevent this Exception.
Documentation says :
public class InputMismatchException extends NoSuchElementException
Thrown by a Scanner to indicate that the token retrieved does not
match the pattern for the expected type, or that the token is out of
range for the expected type.
new Scanner("vertex.txt")
This is a Scanner which reads the passed String (and not a file with that name). Since this String contains a filename and not a number it will fail.
What you're looking for is:
new Scanner(new File("vertex.txt"))
This one will first create a 'File' instance with the given filename and then pass that to the Scanner, so it will actually read the content of this file.
The same applies to your Scanner for the "edges.txt".

Categories

Resources