实际指出你想要什么有点困难,所以我会采取我自己的假设。
- 过滤后底层集合应该保持不变
- 结果不持久
一个经典的方法是使用views。这基本上是惰性编程,您可以在其中创建一个对象,该对象可以访问原始集合并知道要应用的过滤器,但只要不需要任何计算,就不会进行任何计算。
在集合上,视图通常通过以下方式实现迭代器,对于过滤,当然是已经指出的策略模式。
例如:
Collection myCollection;
Predicate myFilter;
// Nothing is computed here
View<Predicate> myView(myCollection, myFilter);
// We iterate until we find the first item in the collection that satisfies
// the Predicate, and no more, to initialize `begin`
View<Predicate>::Iterator begin = myView.begin(), end = myView.end();
净优势是,如果您(比如说)只需要前 10 个项目,那么您只需应用谓词来查找前 10 个项目,而不再需要更多。
而且,所涉及的元素没有副本,即使您修改,您的视图也保证会更新myCollection
,尽管这可能会影响迭代器的有效性(像往常一样)。
问题是(除非您实现缓存),每次都会计算结果。
如果您想要更持久的结果,那么您最好构建一个仅包含过滤项(或对它们的引用)的新集合。这里没有通用模式,因为它取决于您想要如何使用“过滤”列表。
至于建议的策略模式,您通常可以使用复合模式按块构建过滤器,然后将构建的对象作为策略传递。
复合模式特别适合表示解析表达式的结果,例如,您可能想查看表达式树以获得一个想法。