如何使用分区(或其他)连接两个表

Posted

技术标签:

【中文标题】如何使用分区(或其他)连接两个表【英文标题】:How to join two tables using partition (or something else) 【发布时间】:2020-05-22 20:45:52 【问题描述】:

我有两张桌子:

表 A 包含销售产品(test1、test2)以及每天的信息 表 B 包含这些产品的类别更改历史记录(产品可以每年或每天更改一次类别,具体取决于产品)

我想在今天销售当前类别的产品(如果今天改变了类别,我想在今天和以后看到它,在下一次改变之前)

请帮助没有很多子查询(表很重)

    TABLE A >>
        uid  name  date
        1   test1  2019-09-01
        2   test1  2019-09-02
        3   test1  2019-09-03
        4   test2  2019-09-01
        5   test2  2019-09-02
        6   test2  2019-09-03

    TABLE B >>
    uid  name  date_change  category
    1   test1  2019-08-30  cat1
    2   test1  2019-09-02  cat2
    4   test1  2019-09-04  cat3
    5   test2  2019-09-01  cat4
    6   test2  2019-09-03  cat5

    TABLE Result >>
    uid  name  date       date_change  category
    1   test1  2019-09-01  2019-08-30  cat1
    2   test1  2019-09-02  2019-09-02  cat2
    3   test1  2019-09-03  2019-09-02  cat2
    4   test2  2019-09-01  2019-09-01  cat4
    5   test2  2019-09-02  2019-09-01  cat4
    6   test2  2019-09-03  2019-09-03  cat5


【问题讨论】:

【参考方案1】:

以下是 BigQuery 标准 SQL

#standardSQL
SELECT a.name, `date`, date_change, category
FROM `project.dataset.tableA` a
LEFT JOIN(
  SELECT name, date_change, category, 
    DATE_SUB(LEAD(date_change, 1, DATE '2100-01-01') OVER(PARTITION BY name ORDER BY date_change), INTERVAL 1 DAY) last_day
  FROM `project.dataset.tableB` 
) b
ON a.name = b.name 
AND a.date BETWEEN b.date_change AND b.last_day
-- ORDER BY name, date_change

如果适用于您问题的样本数据 - 结果是

Row name    date        date_change category     
1   test1   2019-09-01  2019-08-30  cat1     
2   test1   2019-09-02  2019-09-02  cat2     
3   test1   2019-09-03  2019-09-02  cat2     
4   test2   2019-09-01  2019-09-01  cat4     
5   test2   2019-09-02  2019-09-01  cat4     
6   test2   2019-09-03  2019-09-03  cat5     

【讨论】:

【参考方案2】:

一个选项使用相关子查询从b 中检索datea 之前的最新cat

select 
    a.*,
    (
        select cat 
        from b 
        where b.name = a.name and b.date_changed <= a.date 
        order by b.date_changed desc 
        limit 1
    ) cat
from a

【讨论】:

不支持引用其他表的相关子查询,除非它们可以去相关,例如通过将它们转换为有效的 JOIN。

以上是关于如何使用分区(或其他)连接两个表的主要内容,如果未能解决你的问题,请参考以下文章

Hive 使用分区连接表

如何在没有任何重复行的情况下连接 cognos 中的两个表?

从两个表计算分区并在bigquery中使用小于或等于索引的索引

如何包含两个表中的所有值? group_concat 和其他值

如何将非分区表转换为分区表

如何在没有任何重复行的情况下连接两个表中的表?