Sakib Hasan
Sakib Hasan

Reputation: 451

How parse string into map,the string read from a file location using java

I want to read a file from my driver location and parse the file data into map,the file type text and contain data are given below

dhaka : 1 : jamalpur City : 2
khulna City : 3 : Bangladesh : 1

I am trying to solve this problem,but always unable.Please help me, here is my code

Map < String, Integer > amap = new HashMap < String, Integer > ();
try {
    BufferedReader buf = new BufferedReader(new FileReader("D:\\t.txt"));
    String ss = null;
    while ((ss = buf.readLine()) != null) {
        String[] pair = ss.split(":");
        for (int i = 0; i < pair.length; i += 2)
        amap.put(pair[i], Integer.parseInt(pair[1 + i]));
    }
    buf.close();
    for (Map.Entry em: amap.entrySet()) {
        System.out.println(" " + em.getKey() + " " + em.getValue());
    }
} catch (Exception e) {e.printStackTrace( );}

show java.lang.ArrayIndexOutOfBoundsException please solve this problem

Upvotes: 1

Views: 667

Answers (5)

Ataww
Ataww

Reputation: 21

You have spaces between the : and the values, which cause a NumberFormatException when you try to parse int.

A possible replacement is:

Map < String, Integer > amap = new HashMap < String, Integer > ();
    try {
        BufferedReader buf = new BufferedReader(new FileReader("D:\\t.txt"));
        String ss = null;
        while ((ss = buf.readLine()) != null) {
            String[] pair = ss.split(":");
            for (int i = 0; i < pair.length; i += 2)
            amap.put(pair[i], Integer.parseInt(pair[1 + i].replaceAll("\\s+","")));
        }
        buf.close();
        for (Map.Entry em: amap.entrySet()) {
            System.out.println(" " + em.getKey() + " " + em.getValue());
        }
    } catch (Exception e) {
        e.printStackTrace( ); // shows a NumberFormatException
    }

bhspencer's answer works as well, using ss.split(" : ");

Also, always check your exception when you have issues with your program, they are usually really useful.

Edit: as pointed out by @austinwernli, replacing whitespaces in the whole line would also delete white spaces in multi world entry. Thus the replaceAll function should be applied to pair[i + 1] instead.

Edit 2: ArrayIndexOutOfBoundsException comes from an odd number of value on a line like dhaka : 1 : jamalpur City : 2 : v : 5 : s :

A workaround could be to change the for loop with :

for (int i = 1; i < pair.length; i += 2) {
    amap.put(pair[i - 1], Integer.parseInt(pair[i].replaceAll("\\s+","")));
}

This way the last value is skipped on a list of odd size. I also changed replaceAll to trim as it suits the question better.

Upvotes: 1

Fevly Pallar
Fevly Pallar

Reputation: 3099

for (int i = 0; i < pair.length; i += 2)
    amap.put(pair[i], Integer.parseInt(pair[1 + i]));

should be :

EDIT :

            for (int i = 0; i <pair.length; i +=2) {

                amap.put(pair[i].trim(), Integer.parseInt(pair[(1 + i)].trim()));
            }

ADDITIONAL NOTE :

if you see the elements are not ordered , it's because HashMap doesn't maintain an order, you should change to Map<String, Integer> amap = new LinkedHashMap<String, Integer>(); to see the ordered version of your elements.

MORE ADDITIONAL NOTE :

It will also work where the number of pair of (Key & Value) is different on every line , like :

dhaka : 1 : jamalpur City : 2 : v : 5
khulna City : 3 : Bangladesh : 1 : w : 5
x : 5
y : 9 : m : 2 

Upvotes: 1

Pusker Gy&#246;rgy
Pusker Gy&#246;rgy

Reputation: 398

The space characters around the number caused a NumberFormatException, and there are space characters around city names so change this line

amap.put(pair[i], Integer.parseInt(pair[1 + i]));

to this

amap.put(pair[i].trim(), Integer.parseInt(pair[1 + i].trim()));

It's a really bad practice to leave catch blocks empty, it hides the problem (the NumberFormatException in this case).

Upvotes: 1

bhspencer
bhspencer

Reputation: 13570

You don't say what error you are getting but I expect you are seeing

java.lang.NumberFormatException: For input string: " 1"

Is that correct?

If so the answer is because splitting the String ss with

String[] pair = ss.split(":");

will result in

"dhaka ", " 1 ", " jamalpur City ", " 2"

Where as you want "dhaka", "1", "jamalpur City", "2"

Those extra spaces will prevent the Integers from parsing. I suggest splitting you string with String[] pair = ss.split(" : ");

Upvotes: 1

austin wernli
austin wernli

Reputation: 1801

If you wanted to add a reader as well this should solve your issue. This will only work though if there is no possibility for parts of the pairs being on separate lines.

Map < String, Integer > amap = new HashMap < String, Integer > ();
try {
    BufferedReader buf = new BufferedReader(new FileReader("D:\\t.txt"));
    String ss = null;
    while ((ss = buf.readLine()) != null) {
        String[] ssPairs = ss.split(" : ");
        for (int i = 0; i < splt.length; i += 2) {
            amap.put(ssPairs[i], Integer.parseInt(ssPairs[i + 1]));
        }
    }
    buf.close();
    for (Map.Entry em: amap.entrySet()) {
        System.out.println(" " + em.getKey() + " " + em.getValue());
    }
} catch (Exception e) {}

Upvotes: 1

Related Questions