1

I have a nested map as

Map<String, HashMap<String, Integer>> map = new TreeMap<String, HashMap<String, Integer>>();

Also, I have deep map as

HashMap<String, Integer> deep_map = new HashMap<String, Integer>();

I read lines from txt file and put in to nested map as below

try {
    FileInputStream fstream = new FileInputStream("file.txt");
    DataInputStream in = new DataInputStream(fstream);
    BufferedReader br = new BufferedReader(new InputStreamReader(in));
    String strLine;
    while ((strLine = br.readLine()) != null)  {
        String[] tokens = strLine.split(" ");
        deep_map.put(tokens[1], Integer.parseInt(tokens[2]));
        map.put(tokens[0], deep_map);
    }
    in.close();
} catch (Exception e) {
    System.err.println("Error: " + e.getMessage());
}

Content of txt file like

John AA 80
Adam BB 60
Natalie BB 65

Name is the key of map, grade is the key of nested map and score is the value of nested map. Thus, how can I sort them descending order of score?

khelwood
  • 55,782
  • 14
  • 81
  • 108
I.Bozcan
  • 45
  • 1
  • 7

2 Answers2

1

The map should contain different deep_map instances, as otherwise every key of map would have the same Map object, and you have overwritten values.

So you only need as field:

SortedMap<String, Map<String, Integer>> map = new TreeMap<>();

The reading can go as below. I do not use all features, as that would need much explanation.

Path path = Paths.get("file.txt");
try (Stream<String> lines = Files.lines(path, Charset.defaultCharset()) {
    lines.map(line -> line.split(" "))
            .filter(tokens -> tokens.length == 3)
            .forEach(tokens -> {
                Map<String, Integer> deepMap = map.get(tokens[0]);
                if (deepMap == null) {
                    deepMap = new HashMap<String, Integer>();
                    map.put(tokens[0], deepMap);
                }
                deepMap.put(tokens[1], Integer.parseInt(tokens[2]));
            });
} catch (IOException e) {
    System.err.println("Error: " + e.getMessage());
}

HOWEVER to have data ordered with descending score:

SortedMap<Integer, Map<String, String>> scoreToCourseToName =
    new TreeMap<>(Comparator.reversed());
Path path = Paths.get("file.txt");
try (Stream<String> lines = Files.lines(path, Charset.defaultCharset()) {
    lines.map(line -> line.split(" "))
            .filter(tokens -> tokens.length == 3)
            .forEach(tokens -> {
                Integer score = Integer.valueOf(tokens[2]);
                Map<String, String> deepMap = scoreToCourseToName.get(score);
                if (deepMap == null) {
                    deepMap = new TreeMap<String, Integer>();
                    scoreToCourseToName.put(score, deepMap);
                }
                deepMap.put(tokens[1], Integer.parseInt(tokens[0]));
            });
} catch (IOException e) {
    System.err.println("Error: " + e.getMessage());
}

And with more feature using:

SortedMap<Integer, Map<String, String>> scoreToCourseToName =
    new TreeMap<>(Comparator.reversed());
Path path = Paths.get("file.txt");
try (Stream<String> lines = Files.lines(path, Charset.defaultCharset()) {
    lines.map(line -> line.split(" "))
            .filter(tokens -> tokens.length == 3)
            .forEach(tokens -> {
                Integer score = Integer.valueOf(tokens[2]);
                Map<String, String> deepMap =
                    scoreToCourseToName.computeIfAbsent(score, sc -> new TreeMap<>());
                deepMap.put(tokens[1], Integer.parseInt(tokens[0]));
            });
} catch (IOException e) {
    System.err.println("Error: " + e.getMessage());
}
Joop Eggen
  • 107,315
  • 7
  • 83
  • 138
  • As ı understood, score is key of sortedMap in your code. But it should be value of deepMap. Just should I replace them later ? – I.Bozcan Jan 03 '20 at 16:10
  • Another problem is when there are another row that grade and name are same, program overwrite them, because they keep as key in deepMap together. – I.Bozcan Jan 03 '20 at 17:00
  • So one new problem is reading A B 10 and A B 20 one wants to store the highest probably. Maybe there is a difference what you want to store and what you want to output. You might even think of a `class Student { String name; String course; List scores; }`. – Joop Eggen Jan 03 '20 at 17:19
  • Actually, Problem is A B 10 and C D 10 case because score store as key. Can you share your e-mail address with me sir ? – I.Bozcan Jan 03 '20 at 17:46
  • I would do that normally, but the problem is not that much interesting and as of next Monday I am deep into work. Try to "solve" your problem logically with pen and paper; then you can solve every problem after a while. And do debugging. Good luck – Joop Eggen Jan 03 '20 at 18:20
0

Maps are sorted by the key so I think the best way is to create a new Map which uses score as key and a List of names as value.

But I don't understand your structure.

CodingSamples
  • 194
  • 1
  • 1
  • 7
  • Problem is key of map. I can sort easily nested_map I mean I can sort only 1d hashmap. But I can't keep key of nested map. When I use comparable class, it throws error because value of map is LinkedHashMap. Is it clear enough ? – I.Bozcan Jan 03 '20 at 15:40