【问题标题】:Spring Data MongoDB: how to get an intersection between two lists with aggregate and SetIntersectionSpring Data MongoDB:如何使用聚合和 SetIntersection 获取两个列表之间的交集
【发布时间】:2020-07-06 17:18:29
【问题描述】:

我有一个集合,其中一个字段是整数列表:

myDocument1:{
   _id: 1,
   bits: [0,1,2,9,11,12,19]

},
myDocument2:{
   _id: 2,
   bits: [0,1,3,6,11,12,16]

}

另一方面,我有一个整数查询列表,我想检查与此集合中文档的每个位列表的交集的大小。在原生 MongoDB 查询语言中,我进行如下操作:

query: [2,9,11];

{'$project': {
            'intersectionSize': {'$let': {
                'vars': {'common': {'$size': {'$setIntersection': ['$bits', query ]}}},
            }},
        '_id': 1,
        }}

...我添加到我的聚合管道后(我可以按需添加)。

根据 spring-data 文档,我一直在尝试将 ProjectOperator 与 SetIntersection 一起使用:

List<Integer> list = [2,9,11];          
ProjectionOperation po = project().and(SetOperators.SetIntersection.arrayAsSet("bits")
               .intersects(query).size().as("intersectionSize");

...但是“相交”不接受任何类型的数组或列表。

如何使用 MongoTemplate 和 Spring-Data 对我的集合中的数组和查询数组之间的交集及其大小进行编码?

【问题讨论】:

    标签: aggregation-framework spring-data-mongodb mongotemplate


    【解决方案1】:

    从 spring-data-mongodb v3.0.5 开始,没有接受 List 或其他 CollectionSetOperators.arrayAsSet() 变体。此时,SetOperators.arrayAsSet() 将只接受一个字符串字段引用,或者一个AggregationExpression。我相信这意味着您需要将Literal.asLiteral() 用于AggregationExpression。也许你可以试试这个,或者类似的东西,因为我没有直接测试过:

    List<Integer> list = [2,9,11];          
    ProjectionOperation po = project()
        .and(SetOperators.SetIntersection.arrayAsSet("bits")
            .intersects(Literal.asLiteral(list)).size())
        .as("intersectionSize");
    

    请注意,在调用.size() 之后,我还添加了缺少的括号来关闭投影的.and() 部分,这在您的问题和我写这篇文章时的其他答案中都没有.

    【讨论】:

      猜你喜欢
      • 2013-08-29
      • 2020-04-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多