【问题标题】:Big Query: How to join 2 tables on user ID when 1 table contains an array of user ids?大查询:当 1 个表包含用户 ID 数组时,如何在用户 ID 上连接 2 个表?
【发布时间】:2020-10-08 17:04:59
【问题描述】:

已经在 StackOverflow 上发布了一些类似的答案,但他们没有解决这个具体案例或涉及我无法理解的查询,因为我刚刚开始了我的第一个 SQL 相关职位。

这是我第一次尝试在我要以数组形式加入的表中加入具有列值的表。在尝试解决我自己的问题后,我遇到了以下错误:No matching signature for operator = for argument types: ARRAY<INT64>, STRING

我有 2 个表格,如下所示:

表 1:

team_id     user_id
   1       [1, 2, 3]
   2       [4, 5, 6]
   3       [7, 8, 9]
   4      [10, 11, 12]

表 2:

user_id    value
   2         10
   5         20
   7         30
   12        40

我想通过让表2分析表1的数组中是否有匹配的user_id来将表2加入表1。如果有,则根据常见的user_id进行连接,输出结果如下:

期望的输出

team_id  user_id  value
1          2       10
2          5       20
3          7       30
4          12      40

提前感谢您分享您的知识!

【问题讨论】:

  • 如果 table2 中的多个用户与 table1 中的 team_id 匹配怎么办?
  • @MikhailBerlyant 我目前正在尝试实施已发布的答案,但如果您有时间,我很想看看如果 table2 中超过 1 个用户与 table1 中的 team_id 匹配时如何加入表格
  • I would love to see how ... - 当然。请参阅我的答案。如果有帮助,请考虑投票:o)
  • @MikhailBerlyant 我将在今天晚些时候下班后研究它。感谢您一如既往地分享您的知识。我会尽快回复您

标签: sql arrays google-bigquery inner-join


【解决方案1】:

你可以加入unnest():

select t1.team_id, t2.user_id, t2.value
from table1 t1
inner join table2 t2 on t2.user_id in unnest(t1.user_id)

【讨论】:

    【解决方案2】:

    以下是 BigQuery 标准 SQL

    #standardSQL
    SELECT team_id, 
      ARRAY_AGG(t2.user_id IGNORE NULLS) user_id,
      IFNULL(SUM(value), 0) value
    FROM `project.dataset.table1` t, t.user_id AS user_id
    LEFT JOIN `project.dataset.table2` t2
    USING(user_id)
    GROUP BY team_id
    

    您可以使用与您所讨论的示例数据类似的示例数据进行测试,如以下示例所示

    #standardSQL
    WITH `project.dataset.table1` AS (
      SELECT 1 team_id, [1, 2, 3] user_id UNION ALL
      SELECT 2, [4, 5, 6] UNION ALL
      SELECT 3, [7, 8, 9] UNION ALL
      SELECT 4, [10, 11, 12] UNION ALL
      SELECT 5, [13, 14]
    ), `project.dataset.table2` AS (
      SELECT 2 user_id, 10 value UNION ALL
      SELECT 3, 20 UNION ALL
      SELECT 5, 20 UNION ALL
      SELECT 7, 30 UNION ALL
      SELECT 9, 1 UNION ALL
      SELECT 12, 40 
    )
    SELECT team_id, 
      ARRAY_AGG(t2.user_id IGNORE NULLS) user_id,
      IFNULL(SUM(value), 0) value
    FROM `project.dataset.table1` t, t.user_id AS user_id
    LEFT JOIN `project.dataset.table2` t2
    USING(user_id)
    GROUP BY team_id    
    

    有输出

    【讨论】:

    • 米哈伊尔,谢谢你的例子!正如所承诺的,我今天花时间浏览了这段代码并真正理解了它。了解我以前从未使用过的 IFNULL() 函数非常有帮助,现在我知道它用于避免从零开始的查询错误。我还注意到您如何添加一个额外的极端案例,说明如何处理在另一个表中找不到 user_id 的情况。你总是第一个回答我的问题,谢谢你!我从您的示例中注意到,即使我有一个公共列的数组,JOIN 语法也没有改变。
    猜你喜欢
    • 2014-08-06
    • 2021-05-14
    • 1970-01-01
    • 2021-06-24
    • 1970-01-01
    • 1970-01-01
    • 2018-03-05
    • 1970-01-01
    • 2011-08-18
    相关资源
    最近更新 更多