Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Java List keeps adding the last record, duplicating it for the number of records in file

Tags:

java

arraylist

A weird thing is happening in my code and I'm just not sure whats going on. I have a file that looks like this:

id;state;city;total_pop;avg_temp
1;Florida;;120000;76
2;Michigan;Detroit;330000;54
3;New Jersey;Newark;;34

My java parser should create a list of maps as the result and return. But the only thing that gets returned is the last record in the file repeated for the number of rows in the file. Can someone eye my code and enlighten me as to what is going on? Thank you in advance.

public class FileParserUtil {

    public List<Map<String, String>> parseFile(String fileName, char seperator)
            throws IOException {

        CSVReader reader = new CSVReader(new FileReader(fileName), seperator);
        Map<String, String> record = new HashMap<String, String>();
        List<Map<String, String>> rows = new ArrayList<Map<String, String>>();

        String[] header = reader.readNext();
        String[] nextLine;

        while ((nextLine = reader.readNext()) != null) {
            for (int i = 0; i < header.length; i++) {
                record.put(header[i], nextLine[i]);
            }
            System.out.println("--------Here is the record: ---------");
            System.out.println(record);
            rows.add(record);
            System.out.println("--------Here are the rows: ---------");
            System.out.println(rows);
        }
        reader.close();
        return rows;

    }
}

Here is the console output of the above run from a main method...

--------Here is the record: ---------
{id=1, avg_temp=76, state=Florida, total_pop=120000, city=}
--------Here are the rows: ---------
[{id=1, avg_temp=76, state=Florida, total_pop=120000, city=}]
--------Here is the record: ---------
{id=2, avg_temp=54, state=Michigan, total_pop=330000, city=Detroit}
--------Here are the rows: ---------
[{id=2, avg_temp=54, state=Michigan, total_pop=330000, city=Detroit}, {id=2, avg_temp=54, state=Michigan, total_pop=330000, city=Detroit}]
--------Here is the record: ---------
{id=3, avg_temp=34, state=New Jersey, total_pop=, city=Newark}
--------Here are the rows: ---------
[{id=3, avg_temp=34, state=New Jersey, total_pop=, city=Newark}, {id=3, avg_temp=34, state=New Jersey, total_pop=, city=Newark}, {id=3, avg_temp=34, state=New Jersey, total_pop=, city=Newark}]
like image 591
Horse Voice Avatar asked Oct 11 '13 12:10

Horse Voice


4 Answers

I think that you forgot to replace record with new empty map, after it is added to list. You want something like this:

rows.add(record);
record = new HashMap<String, String>();
like image 174
Paperback Writer Avatar answered Oct 02 '22 23:10

Paperback Writer


it is because in a HashMap you cannot have duplicate values.. so, when you do this

record.put("id","1");

it will check if there is already a key named "id", if it does it will replace its old value with the new value. At the first iteration it won't replace anything but from the next iteration it will start replacing the old values.

And when you add

row.add(record);

you are adding the same reference again and again, and since the map contains only the newly inserted value the same reference's toString() method is called and the same value is printed again and again.

you should have added

record = new HashMap<String,String>();

to add a new map for each record.

like image 26
Thirumalai Parthasarathi Avatar answered Oct 03 '22 00:10

Thirumalai Parthasarathi


while ((nextLine = reader.readNext()) != null) {
    Map<String, String> record = new HashMap<String, String>();
...
}

You are reusing the same instance of a map all the time, values get overwritten. I would also recommend to create a separate class for storing your data, it would be cleaner.

like image 33
Admit Avatar answered Oct 02 '22 23:10

Admit


You should move following line

Map<String, String> record = new HashMap<String, String>();

within for loop :

public class FileParserUtil {

    public List<Map<String, String>> parseFile(String fileName, char seperator)
            throws IOException {

        CSVReader reader = new CSVReader(new FileReader(fileName), seperator);
        List<Map<String, String>> rows = new ArrayList<Map<String, String>>();

        String[] header = reader.readNext();
        String[] nextLine;

        while ((nextLine = reader.readNext()) != null) {
            Map<String, String> record = new HashMap<String, String>();
            for (int i = 0; i < header.length; i++) {
                record.put(header[i], nextLine[i]);
            }
            System.out.println("--------Here is the record: ---------");
            System.out.println(record);
            rows.add(record);
            System.out.println("--------Here are the rows: ---------");
            System.out.println(rows);
        }
        reader.close();
        return rows;

    }
}
like image 37
user987339 Avatar answered Oct 02 '22 23:10

user987339