【问题标题】:Is it possible to input the result of one query as a condition in another query MongoDB是否可以在另一个查询MongoDB中输入一个查询的结果作为条件
【发布时间】:2021-02-26 15:25:15
【问题描述】:

这是我在 MySQL 上的查询:

select date, AVG(retail_and_recreation_percent_change_from_baseline),
AVG(grocery_and_pharmacy_percent_change_from_baseline),
AVG(workplaces_percent_change_from_baseline)
from global_mobility_report
where date >=
    (select date
    from owid_covid_data
    where location like "Indonesia"
    and CAST(total_cases as signed) > 20000
    order by date
    limit 1)
and country_region like "Indonesia"
group by date
order by date

我想在 MongoDB 上做类似的事情,但我必须采取 2 个步骤:

第 1 步:查找日期

db.ovid2.aggregate([
    {$match:{"location":"Indonesia"}},    
    {$match:{"total_cases":{$gt:20000}}},
    {$sort:{date:1}},
    {$project:{_id:0, date:1}}
    {$limit:1}
    ])

output: ISODate("2020-05-22T00:00:00.000+08:00")

第 2 步:手动输入日期并继续其余的查询

    db.mobility.aggregate([
        {$match:{"country_region":"Indonesia"}},    
        {$match:{"date":{$gte:ISODate("2020-05-22T00:00:00.000+08:00")}}},
        {$group:{_id:"$date",
            AvgRandR:{$avg:"$retail_and_recreation_percent_change_from_baseline"},
            AvgGandP:{$avg:"$grocery_and_pharmacy_percent_change_from_baseline"},
            AvgW:{$avg:"$workplaces_percent_change_from_baseline"}}},
        {$sort:{_id:1}}
        ])

有没有更简单的方法来做到这一点?我意识到这不是最优的,特别是如果问题发生变化并且第 1 步返回多个输出(比如超过 100 个)。这意味着我必须在第 2 步中输入 100 个不同的值?

以下是一些示例文档:

  • 集合:流动性
    {
        "_id" : ObjectId("5f49fd6a3acddb5eec4427bb"),
        "country_region_code" : "ID",
        "country_region" : "Indonesia",
        "sub_region_1" : "",
        "sub_region_2" : "",
        "metro_area" : "",
        "iso_3166_2_code" : "",
        "census_fips_code" : "",
        "date" : ISODate("2020-02-15T08:00:00.000+08:00"),
        "retail_and_recreation_percent_change_from_baseline" : -2,
        "grocery_and_pharmacy_percent_change_from_baseline" : -2,
        "parks_percent_change_from_baseline" : -8,
        "transit_stations_percent_change_from_baseline" : 1,
        "workplaces_percent_change_from_baseline" : 5,
        "residential_percent_change_from_baseline" : 1
    },
    {
        "_id" : ObjectId("5f49fd6a3acddb5eec44281f"),
        "country_region_code" : "ID",
        "country_region" : "Indonesia",
        "sub_region_1" : "",
        "sub_region_2" : "",
        "metro_area" : "",
        "iso_3166_2_code" : "",
        "census_fips_code" : "",
        "date" : ISODate("2020-05-25T08:00:00.000+08:00"),
        "retail_and_recreation_percent_change_from_baseline" : -40,
        "grocery_and_pharmacy_percent_change_from_baseline" : -17,
        "parks_percent_change_from_baseline" : -16,
        "transit_stations_percent_change_from_baseline" : -59,
        "workplaces_percent_change_from_baseline" : -70,
        "residential_percent_change_from_baseline" : 19
    },
    {
        "_id" : ObjectId("5f49fd6a3acddb5eec4428db"),
        "country_region_code" : "ID",
        "country_region" : "Indonesia",
        "sub_region_1" : "Aceh",
        "sub_region_2" : "",
        "metro_area" : "",
        "iso_3166_2_code" : "ID-AC",
        "census_fips_code" : "",
        "date" : ISODate("2020-05-22T08:00:00.000+08:00"),
        "retail_and_recreation_percent_change_from_baseline" : -4,
        "grocery_and_pharmacy_percent_change_from_baseline" : 33,
        "parks_percent_change_from_baseline" : -10,
        "transit_stations_percent_change_from_baseline" : -33,
        "workplaces_percent_change_from_baseline" : -31,
        "residential_percent_change_from_baseline" : 9
    }
  • 收藏:ovid2
    {
        "_id" : ObjectId("5f4a06e23acddb5eec55a4aa"),
        "iso_code" : "IDN",
        "continent" : "Asia",
        "location" : "Indonesia",
        "date" : ISODate("2020-05-22T00:00:00.000+08:00"),
        "total_cases" : 20162,
        "new_cases" : 973,
        "new_cases_smoothed" : 593.714,
        "total_deaths" : 1278,
        "new_deaths" : 36,
        "new_deaths_smoothed" : 33.571,
        "total_cases_per_million" : 73.712,
        "new_cases_per_million" : 3.557,
        "new_cases_smoothed_per_million" : 2.171,
        "total_deaths_per_million" : 4.672,
        "new_deaths_per_million" : 0.132,
        "new_deaths_smoothed_per_million" : 0.123,
        "new_tests" : 0,
        "total_tests" : 168969,
        "total_tests_per_thousand" : 0.618,
        "new_tests_per_thousand" : 0,
        "new_tests_smoothed" : 5273,
        "new_tests_smoothed_per_thousand" : 0.019,
        "tests_per_case" : 8.881,
        "positive_rate" : 0.113,
        "tests_units" : NaN,
        "stringency_index" : 71.76,
        "population" : 273523621,
        "population_density" : 145.725,
        "median_age" : 29.3,
        "aged_65_older" : 5.319,
        "aged_70_older" : 3.053,
        "gdp_per_capita" : 11188.744,
        "extreme_poverty" : 5.7,
        "cardiovasc_death_rate" : 342.864,
        "diabetes_prevalence" : 6.32,
        "female_smokers" : 2.8,
        "male_smokers" : 76.1,
        "handwashing_facilities" : 64.204,
        "hospital_beds_per_thousand" : 1.04,
        "life_expectancy" : 71.72
    },
    {
        "_id" : ObjectId("5f4a06e23acddb5eec55a420"),
        "iso_code" : "IDN",
        "continent" : "Asia",
        "location" : "Indonesia",
        "date" : ISODate("2020-01-05T00:00:00.000+08:00"),
        "total_cases" : 0,
        "new_cases" : 0,
        "new_cases_smoothed" : 0,
        "total_deaths" : 0,
        "new_deaths" : 0,
        "new_deaths_smoothed" : 0,
        "total_cases_per_million" : 0,
        "new_cases_per_million" : 0,
        "new_cases_smoothed_per_million" : 0,
        "total_deaths_per_million" : 0,
        "new_deaths_per_million" : 0,
        "new_deaths_smoothed_per_million" : 0,
        "new_tests" : 0,
        "total_tests" : 0,
        "total_tests_per_thousand" : 0,
        "new_tests_per_thousand" : 0,
        "new_tests_smoothed" : 0,
        "new_tests_smoothed_per_thousand" : 0,
        "tests_per_case" : 0,
        "positive_rate" : 0,
        "tests_units" : 0,
        "stringency_index" : 5.56,
        "population" : 273523621,
        "population_density" : 145.725,
        "median_age" : 29.3,
        "aged_65_older" : 5.319,
        "aged_70_older" : 3.053,
        "gdp_per_capita" : 11188.744,
        "extreme_poverty" : 5.7,
        "cardiovasc_death_rate" : 342.864,
        "diabetes_prevalence" : 6.32,
        "female_smokers" : 2.8,
        "male_smokers" : 76.1,
        "handwashing_facilities" : 64.204,
        "hospital_beds_per_thousand" : 1.04,
        "life_expectancy" : 71.72
    },
    {
        "_id" : ObjectId("5f4a06e63acddb5eec55fbf3"),
        "iso_code" : "ZWE",
        "continent" : "Africa",
        "location" : "Zimbabwe",
        "date" : ISODate("2020-03-21T00:00:00.000+08:00"),
        "total_cases" : 1,
        "new_cases" : 1,
        "new_cases_smoothed" : 0,
        "total_deaths" : 0,
        "new_deaths" : 0,
        "new_deaths_smoothed" : 0,
        "total_cases_per_million" : 0.067,
        "new_cases_per_million" : 0.067,
        "new_cases_smoothed_per_million" : 0,
        "total_deaths_per_million" : 0,
        "new_deaths_per_million" : 0,
        "new_deaths_smoothed_per_million" : 0,
        "new_tests" : 0,
        "total_tests" : 0,
        "total_tests_per_thousand" : 0,
        "new_tests_per_thousand" : 0,
        "new_tests_smoothed" : 0,
        "new_tests_smoothed_per_thousand" : 0,
        "tests_per_case" : 0,
        "positive_rate" : 0,
        "tests_units" : 0,
        "stringency_index" : 27.78,
        "population" : 14862927,
        "population_density" : 42.729,
        "median_age" : 19.6,
        "aged_65_older" : 2.822,
        "aged_70_older" : 1.882,
        "gdp_per_capita" : 1899.775,
        "extreme_poverty" : 21.4,
        "cardiovasc_death_rate" : 307.846,
        "diabetes_prevalence" : 1.82,
        "female_smokers" : 1.6,
        "male_smokers" : 30.7,
        "handwashing_facilities" : 36.791,
        "hospital_beds_per_thousand" : 1.7,
        "life_expectancy" : 61.49
    }

【问题讨论】:

  • 我认为可以使用$lookup 来完成。您能否发布两个集合中的示例文档,以便我们编写查询。

标签: mongodb mongodb-query aggregation-framework


【解决方案1】:

你可以试试,

  • $match您需要的条件
  • $lookupowid_covid_data 使用聚合管道收集并在 owid_covid_data 字段中获取结果,
    • $match您需要的条件
    • $project 必填字段
    • $sort by date 升序
    • $limit 要返回的第 1 个文档
    • $match日期条件
  • $unwind 解构 owid_covid_data 数组,这将删除空结果文档
  • $group by date 和平均字段
  • $sort 按日期升序排列
db.global_mobility_report.aggregate([
  { $match: { country_region: "Indonesia" } },
  {
    $lookup: {
      from: "owid_covid_data",
      let: { date: "$date" },
      pipeline: [
        {
          $match: {
            location: "Indonesia",
            total_cases: { $gt: 20000 }
          }
        },
        { $project: { _id: 0, date: 1 } },
        { $sort: { date: 1 } },
        { $limit: 1 },
        { $match: { $expr: { $gte: ["$$date", "$date"] } } }
      ],
      as: "owid_covid_data"
    }
  },
  { $unwind: "$owid_covid_data" },
  {
    $group: {
      _id: "$date",
      AvgRandR: { $avg: "$retail_and_recreation_percent_change_from_baseline" },
      AvgGandP: { $avg: "$grocery_and_pharmacy_percent_change_from_baseline" },
      AvgW: { $avg: "$workplaces_percent_change_from_baseline" }
    }
  },
  { $sort: { _id: 1 } }
])

Playground

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-04-24
    • 1970-01-01
    • 1970-01-01
    • 2021-07-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多