集合removeAll方法
我想知道下面的内容是否可行,
list.removeAll(namesToRemove)
我希望上下文是可以理解的。
该list
的类型为ArrayList
,其中MyObject
具有getName
方法。
namesToRemove
是一个ArrayList
包含要删除的对象的名称。
我知道这可以通过重写MyObject
类中的equals方法来实现。 我想知道是否还有其他选择。
您可以使用Google Collections Collections2.filter()
:
final List namesToKeep = getNamesToFilter(); List filtered = Collections2.filter(originalList, new Predicate () { @Override public boolean apply(MyObject o) { return namesToKeep.contains(o.getName()); } });
Java 8:
list.removeIf(obj -> namesToRemove.contains(obj.getName()));
Java 7及更早版本:
Iterator iter = list.iterator(); while (iter.hasNext()) if (namesToRemove.contains(iter.next().getName())) iter.remove();
请注意,两种选择都具有二次复杂性。 你可以做到线性化
Set namesToRemoveSet = new HashSet<>(namesToRemove);
在片段之前,使用namesToRemoveSet
而不是namesToRemove
。
您不希望覆盖Object类中的任何内容。 您需要使用filter实用程序或使用您自己的语义而不是equals的集合,也可以使用围绕您自己的等效实现的ForwardingCollection 。
所有这一切都可以通过谷歌番石榴实现,而不会违反任何标准
另一种方法:子类ArrayList
并实现一个自定义方法,如:
public class MyArrayList extends ArrayList { // all needed constructors public void removeAllWithNames(Collection names) { // following code is based on aioobe's answer Iterator iter = iterator(); while (iter.hasNext()) if (names.contains(iter.next().toString())) iter.remove(); } }
编辑改变了代码 – 评论很好,现在自定义列表再次是’列表’,但现在我们使用toString()
方法(为简单起见)进行过滤。 (使用getName()
方法是可能的,但需要更多行代码)
Collection list = Collections2.filter(list, mo -> !namesToRemove.contains(mo.getName()));