Bigquery Innerjoin 运行了很长时间
Posted
技术标签:
【中文标题】Bigquery Innerjoin 运行了很长时间【英文标题】:Bigquery Innerjoin is running for very long time 【发布时间】:2019-11-14 18:56:29 【问题描述】:我有两个大小为 13 GB 和 1 GB 的表。表 1 有 1200 万行 * 1.6k 列,表 2 有 5k 行 * 160 列。 我正在对这两个表执行内部连接以查找所有匹配记录,如下面的示例查询,但查询似乎运行了很长时间,几个小时。结果连接的表大小为 29 GB,包含 900 万行。 我应该如何提高此操作的运行时间?我确实读过对表进行聚类可以提高性能。这是这种情况下的最佳选择吗?
SELECT
*
FROM
`myproject.table1` as t1
INNER JOIN
`myproject.table2` as t2
ON
(
t1.Camp1ID = t2.ID
OR t1.Camp2ID = t2.ID
OR t1.Camp3ID = t2.ID
OR t1.Camp4ID = t2.ID
OR t1.Camp5ID h = t2.ID
OR t1.Camp6ID = t2.ID
OR t1.Camp7ID = t2.ID
OR t1.Camp8ID = t2.ID
OR t1.Camp9ID = t2.ID
OR t1.Camp10ID = t2.ID
OR t1.Camp11ID = t2.ID
OR t1.Camp12ID = t2.ID
OR t1.Camp13ID = t2.ID
OR t1.Camp14ID = t2.ID
OR t1.Camp15ID = t2.ID
OR t1.Camp16ID = t2.ID
)
Where
t1.Date BETWEEN PARSE_DATE('%m/%d/%y', t2.StartDate) AND PARSE_DATE('%m/%d/%y', t2.EndDate)
阵营 ID 在这些列中不是唯一的,多行具有相同的阵营 ID。
【问题讨论】:
您的文字提到了两张表格,但您的问题只有一张。您正在使用or
和 20 列对表进行自联接。你知道这可能产生多少行吗?示例数据、所需结果以及对您想要的逻辑的解释都会有所帮助。
对不起它的表 2,不是自联接。期望的结果是有一个表,其中两个表中的所有列都具有匹配的行。
【参考方案1】:
一些改进(BigQuery 标准 SQL)
#standardSQL
SELECT * EXCEPT(parsed_StartDate, parsed_EndDate)
FROM `myproject.table1` as t1
INNER JOIN (SELECT * ,
PARSE_DATE('%m/%d/%y', t2.StartDate) parsed_StartDate,
PARSE_DATE('%m/%d/%y', t2.EndDate) parsed_EndDate
FROM `myproject.table2`
) as t2
ON t2.ID IN (t1.Camp1ID,t1.Camp2ID,t1.Camp3ID,t1.Camp4ID,t1.Camp5ID,t1.Camp6ID,t1.Camp7ID,t1.Camp8ID,t1.Camp9ID,t1.Camp10ID,t1.Camp11ID,t1.Camp12ID,t1.Camp13ID,t1.Camp14ID,t1.Camp15ID,t1.Camp16ID)
AND t1.Date BETWEEN parsed_StartDate AND parsed_EndDate
【讨论】:
此查询将运行时间提高了 ~ 30%。 是的,我希望得到这样的结果 - 主要是因为预解析日期 但是这个查询输出比我在问题中提到的查询输出少了 31k 条记录。 尝试用 WHERE 替换 AND - 因为它在您的查询中【参考方案2】:我确实阅读了对表进行聚类可以提高性能。这是本案的最佳选择吗?
如果您暗示您没有设置正确的索引,并在 13GB 表上进行自联接,我想我发现了您的问题。在其中涉及的每一列、这些营地 ID 和 ID 字段本身上添加单独的非聚集索引。
然后,删除所有硬编码的阵营 ID 列,并与中间表建立适当规范化的一对多关系,然后通过它加入。
【讨论】:
并正确设置索引,在索引中包含所有需要的列,否则无论如何它都必须查找数据。以上是关于Bigquery Innerjoin 运行了很长时间的主要内容,如果未能解决你的问题,请参考以下文章