1

I need to search a value in TreeMap with partial key

I tried with HashMap but its failing

TreeMap<String, BigDecimal> mapYr1 = new TreeMap<String, BigDecimal>();

mapYr1.put("abcdef",100.00);

Is it possible to retrieve value of 100.00 with something like below?

mapYr1.get("abcd");

Here I only know "abcd". I'm not sure "ef" part of key.

Mureinik
  • 297,002
  • 52
  • 306
  • 350
Java Team
  • 65
  • 1
  • 9
  • [This question](https://stackoverflow.com/questions/6713239/partial-search-in-hashmap) seems relevant to yours. – Tim Biegeleisen Jun 21 '19 at 12:52
  • 1
    Trie data structure seems relevant here but this is still tricky. Let' say we have keys in map as `abc` and `abcd` and all you have is `ab`. Which one would you select because there is more than 1 key in the map with the same prefix? – nice_dev Jun 21 '19 at 13:07

1 Answers1

1

Not directly, but you can go over the entries and search for it:

public static BigDecimal findPartialKey(Map<String, BigDecimal> map, String search) {
    return map.entrySet()
              .stream()
              .filter(e -> e.getKey().startsWith(search))
              .map(Map.Entry::getValue)
              .findFirst()
              .orElse(null);
}

Note the using a stream like this, while (questionably) elegant, doesn't take advantage of the fact that the keys in a TreeMap are sorted, and may waste time looking for a matching key in a region that can't contain it. Using a good old-fashioned loop may be a bit clunkier, but in the general case, should perform a bit better:

public static BigDecimalfindPartialKey(SortedMap<String, BigDecimal> map, String search) {
    Iterator<Map.Entry<String, Double>> iter = map.entrySet().iterator();
    while (iter.hasNext()) {
        Map.Entry<String, Double> entry = iter.next();
        String key = entry.getKey();
        if (key.startsWith(search)) {
            return entry.getValue();
        }
        if (key.compareTo(search) > 0) {
            return null;
        }
    }
    return null;
}
Mureinik
  • 297,002
  • 52
  • 306
  • 350