是否有带有自定义比较器的retainAll() 实现?
我需要根据其他集合的内容筛选集合。通常,我会使用Collection.retainAll()
方法。
不幸的是,我正在处理的域对象的相等性相当不稳定,具体取决于比较上下文。因此,我不能依赖equals/hashCode
。
我的下一个反应是使用自定义的Comparator
,但我无法找到任何支持我的想法的方法。实现该功能不是问题,但我想在这里重新发明轮子。
我是否错过了 API 中的某些内容?其他框架(不太深奥),比如 commons 也受欢迎。
如果没有,什么优化将使我的简单实现(通过遍历 n^2 中两个集合的所有项目来创建两个集合内所有对象的列表)好的吗?
I need to sift Collections according to contents of other Collections. Usually, I would have used the Collection.retainAll()
method.
Unfortunately, the equality of the domain objects I am handling is rather volatile, depending on the comparison context. Thus, I cannot rely on equals/hashCode
.
My next reflex was to use a custom Comparator
, but I was unable to find any methods supporting what I had in mind. Implementing the functionality is not a problem but I feel like reinventing the wheel here.
Have I missed something in the API? Other frameworks (not too esoteric) like commons are welcome too.
And if not, what optimizations would make my straightforward impl (creating a list of all Objects inside both Collections by going over all items of both Collections in n^2) a good one?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
建议使用 Guava 的过滤器。另一种方法是推出您自己的
retainAllBy(sourceCollection, Comparator)
。Suggest using Guava's filter. Alternative is to roll your own
retainAllBy(sourceCollection, Comparator)
.Guava 对于这个问题有一个麻烦的解决方案,
等效
概念。您可以使用Equivalence.wrap()
,将包装版本存储在集合中,从而使集合使用您的自定义 equals / hashcode 逻辑。我(和其他人)请求了基于等价的集合和地图,但不幸的是Guava团队建议改用上面的路线。
Guava has a cumbersome solution to this problem, the
Equivalence
concept. You wrap your objects in an equivalence usingEquivalence.wrap()
, store the wrapped versions in collections and thereby make the collections use your custom equals / hashcode logic.I (and others) have requested Equivalence-based sets and maps, but unfortunately the Guava team suggests that the above route should be taken instead.
Java 集合框架中没有任何东西可以通过标准
equals
实现以外的任何其他方式来执行retainAll
操作。很大程度上取决于您的用例,您可以这样做:
创建一个包装对象,它可以包装您的对象,但使用您需要的
equals
方法。然后使用该包装器执行retainAll
之后,您需要从结果集合中解开对象。但这种方式有两个缺点:
There is nothing in the Java Collection Framework that do a
retainAll
by anything else then the standardequals
implementation.Strongly depending on your usecase you can do it this way:
Create a Wrapper Object, that can be wrapped about your Objects, but with the
equals
method you need. And then use that wrappers to do theretainAll
afterwards you need to unwrap the objects from the resulting collection.But this way has two drawbacks:
equals
method of the wrapper is still a valid equals method in terms of the java doc for equals methods.