Сначала я скажу, что вы не должны использовать Double для ключа на карте.Подробнее здесь: Удвоение в HashMap
Далее приведен пример с Map<Integer, Integer>
для упрощения логики.Вам нужно будет адаптировать его для Map<Double, Double>
Логика заключается в том, что первая и последняя записи карты всегда будут в карте результатов.Так что вам просто нужно отфильтровать те, что в середине (индекс 1 к размеру карты -1).Просто пропустите те, которые имеют то же значение, что и предыдущий или следующий
Для версии цикла
// get the sorted list of keys
List<Integer> keys = new ArrayList<>(map.keySet());
Collections.sort(keys);
List<Integer> resultKeys = new ArrayList<>();
// first key will always be in the result map, add it
resultKeys.add(keys.get(0));
// for each following key, add if the value is different from both previous or next
for (int i = 1; i < keys.size()-1; i++) {
Integer key = keys.get(i);
Integer value = map.get(key);
Integer previousKey = keys.get(i-1);
Integer previousValue = map.get(previousKey);
Integer nextKey = keys.get(i+1);
Integer nextValue = map.get(nextKey);
if(previousValue.intValue() != value.intValue() || nextValue.intValue() != value.intValue()) {
resultKeys.add(key);
}
}
// last key will always be in the result map, add it
resultKeys.add(keys.get(keys.size()-1));
// make a map out of you list
Map<Integer, Integer> resultMap = resultKeys.stream()
.collect(Collectors.toMap(k -> k, map::get));
Map<Integer, Integer> resultTreeMap = new TreeMap<>();
resultTreeMap.putAll(resultMap);
Лямбда-версия
// get the sorted list of keys
List<Integer> keys = new ArrayList<>(map.keySet());
Collections.sort(keys);
Map<Integer, Integer> resultMap =
IntStream.range(1, keys.size()-1)
.boxed()
.map(i -> setToNullIfNotKept(keys, i))
.filter(Objects::nonNull)
.collect(Collectors.toMap(k -> k, map::get));
// first key will always be in the result map, add it
resultMap.put(keys.get(0), map.get(keys.get(0)));
// last key will always be in the result map, add it
Integer lastKey = keys.get(keys.size() - 1);
resultMap.put(lastKey, map.get(lastKey));
Map<Integer, Integer> resultTreeMap = new TreeMap<>();
resultTreeMap.putAll(resultMap);
Утилита метод, чтобы обнулить неРазыскиваемые индексы:
private static Integer setToNullIfNotKept(List<Integer> keys, Integer i) {
Integer key = keys.get(i);
Integer value = map.get(key);
Integer previousKey = keys.get(i-1);
Integer previousValue = map.get(previousKey);
Integer nextKey = keys.get(i+1);
Integer nextValue = map.get(nextKey);
if(previousValue.intValue() != value.intValue() || nextValue.intValue() != value.intValue()) {
return key;
}
return null;
}
Выходные данные
Учитывая, что входная карта:
Map<Integer, Integer> map = new TreeMap<>();
map.put(1, 1);
map.put(2, 1);
map.put(3, 1);
map.put(4, 1);
map.put(5, 2);
map.put(6, 2);
map.put(7, 2);
map.put(8, 1);
map.put(9, 1);
map.put(10, 1);
Они оба выводят следующую карту:
{1=1, 4=1, 5=2, 7=2, 8=1, 10=1}