如何比较 Map 和 List
How to compare Map with List
对不起,我找不到更好的标题,而且我知道这听起来很混乱。
问题如下:
我有一个 HashMap,如下所示:
Map<String, ClassA> myMap;
此外,我有一个如下所示的列表:
List<ClassB> myList;
B 类如下所示:
public class ClassB{
//many things
private String someString;
//getter
//setter
}
}
someString 是关键字符串myMap
我想从地图中删除所有我在列表myList
中找不到的objects,迭代次数最少,因为这种清理每隔几秒就会发生一次一生一世。
有算法吗?模式甚至示例?
谢谢
您必须至少迭代 List<ClassB> myList
一次才能这样做,但您可以精确地进行一次迭代,这使其成为理想的算法。
创建一个新地图,并为列表中的每个元素检查它是否在 myMap
中,如果存在 - 将其添加到您创建的新地图中。完成迭代列表后,只需分配:myMap = newMap;
就大功告成了。
注意:这是最少步数的理想选择,但它比"in-place"算法使用更多内存。
有java 8 流API,
Set<String> keySet = new HashSet<>(myMap.keySet());
myList.forEach(entry -> keySet.remove(entry.getSomeString()));
keySet.forEach(key -> myMap.remove(key));
就是这样。我刚刚所做的只是从 keySet
中删除了列表中的键。然后,我删除所有剩下的键。这将在 O(n)
.
中 运行
这将比当前解决方案消耗更少的内存,因为您要创建一个额外的 Set
而不是 Map
。
看起来你想要 retainAll
。诀窍是您在地图的 keySet()
上调用它,它具有从地图中删除不需要的条目的副作用。
接下来,您想要保留的元素不在 List<ClassB>
中,而是在从 ClassB
的每个实例派生的字符串列表中。您可以使用流来做到这一点。
myMap.keySet()
.retainAll(myList.stream()
.map(ClassB::getSomeString)
.collect(toList()));
对不起,我找不到更好的标题,而且我知道这听起来很混乱。 问题如下:
我有一个 HashMap,如下所示:
Map<String, ClassA> myMap;
此外,我有一个如下所示的列表:
List<ClassB> myList;
B 类如下所示:
public class ClassB{
//many things
private String someString;
//getter
//setter
}
}
someString 是关键字符串myMap
我想从地图中删除所有我在列表myList
中找不到的objects,迭代次数最少,因为这种清理每隔几秒就会发生一次一生一世。
有算法吗?模式甚至示例?
谢谢
您必须至少迭代 List<ClassB> myList
一次才能这样做,但您可以精确地进行一次迭代,这使其成为理想的算法。
创建一个新地图,并为列表中的每个元素检查它是否在 myMap
中,如果存在 - 将其添加到您创建的新地图中。完成迭代列表后,只需分配:myMap = newMap;
就大功告成了。
注意:这是最少步数的理想选择,但它比"in-place"算法使用更多内存。
有java 8 流API,
Set<String> keySet = new HashSet<>(myMap.keySet());
myList.forEach(entry -> keySet.remove(entry.getSomeString()));
keySet.forEach(key -> myMap.remove(key));
就是这样。我刚刚所做的只是从 keySet
中删除了列表中的键。然后,我删除所有剩下的键。这将在 O(n)
.
这将比当前解决方案消耗更少的内存,因为您要创建一个额外的 Set
而不是 Map
。
看起来你想要 retainAll
。诀窍是您在地图的 keySet()
上调用它,它具有从地图中删除不需要的条目的副作用。
接下来,您想要保留的元素不在 List<ClassB>
中,而是在从 ClassB
的每个实例派生的字符串列表中。您可以使用流来做到这一点。
myMap.keySet()
.retainAll(myList.stream()
.map(ClassB::getSomeString)
.collect(toList()));