Bigquery 条件拆分聚合失败
Bigquery conditional split aggregations fail
我有一个类别列,其中包含一个字符串,其中包含位于由“|”分隔的可变位置的子类别字段。每个子类别的位置取决于字符串中的项目数。例如:
category subcat1 subcat2 subcat3
a|b|c b c a
x|y|a|b b null a
所以,为了解决一个类别,我有:
SELECT
a.category AS category,
case
WHEN COUNT(SPLIT(a.category, "|")) = 4 then nth(4, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 3 then nth(2, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 2 then nth(2, SPLIT(a.category, "|"))
else null
end as subcat1,
--nth(2, SPLIT(a.category, "|")) as x --uncomment for success. see below
FROM
[interim_groups.articles_unique] as a
运行 这失败了:
SELECT clause has mix of aggregations 'subcat1' and fields 'category' without GROUP BY clause
现在我不想要 group by
子句,拥有一个子句也没有意义,但如果我包含它,它就会开始抱怨作用域聚合,这似乎在错误的方向上进行。
如果我使用 if
语句而不是 case
语句,也会发生同样的情况。
奇怪的地方来了。如果我的查询中有注释行(或者 last(SPLIT(a.category, "|")) as x
),查询将完美通过。
这是一个错误吗?我的查询看起来是正确的,并且在我的查询中有一个额外的列以某种方式让它通过是很奇怪的。
有没有比只保留不必要的列来稳定查询更好的方法来解决这个问题?
我认为使用 String functions 可以相对轻松地提取管道分隔字符串中的最后一个组件
同时,使用 Regular expression functions 的以下版本 - 对于可能更复杂的场景来说它更强大一些
SELECT
a.category AS category,
CASE
WHEN LENGTH(REGEXP_REPLACE(a.category, r"[^|]", "")) = 4
THEN REGEXP_EXTRACT(a.category, r'\|\w+\|\w+\|\w+\|(\w+)')
WHEN LENGTH(REGEXP_REPLACE(a.category, r"[^|]", "")) = 3
THEN REGEXP_EXTRACT(a.category, r'\|\w+\|\w+\|(\w+)')
WHEN LENGTH(REGEXP_REPLACE(a.category, r"[^|]", "")) = 2
THEN REGEXP_EXTRACT(a.category, r'\|\w+\|(\w+)')
ELSE NULL
END AS subcat1
FROM your_table a
没有分组,没有所问的不必要的列!
查询缺少 'WITHIN RECORD' 关键字。
SELECT
a.category AS category,
case
WHEN COUNT(SPLIT(a.category, "|")) = 4 then nth(4, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 3 then nth(2, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 2 then nth(2, SPLIT(a.category, "|"))
else null
end WITHIN RECORD as subcat1 ,
FROM (SELECT category FROM
(SELECT 'a|b|c' category), (SELECT 'a|b' category), (SELECT 'a|b|c|d' category)) a
请参阅 WITHIN 的文档:
WITHIN 关键字专门与聚合函数一起使用,以聚合记录和嵌套字段中的子字段和重复字段。当您指定 WITHIN 关键字时,您需要指定要聚合的范围 -
WITHIN RECORD:聚合记录中重复值中的数据。
我有一个类别列,其中包含一个字符串,其中包含位于由“|”分隔的可变位置的子类别字段。每个子类别的位置取决于字符串中的项目数。例如:
category subcat1 subcat2 subcat3
a|b|c b c a
x|y|a|b b null a
所以,为了解决一个类别,我有:
SELECT
a.category AS category,
case
WHEN COUNT(SPLIT(a.category, "|")) = 4 then nth(4, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 3 then nth(2, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 2 then nth(2, SPLIT(a.category, "|"))
else null
end as subcat1,
--nth(2, SPLIT(a.category, "|")) as x --uncomment for success. see below
FROM
[interim_groups.articles_unique] as a
运行 这失败了:
SELECT clause has mix of aggregations 'subcat1' and fields 'category' without GROUP BY clause
现在我不想要 group by
子句,拥有一个子句也没有意义,但如果我包含它,它就会开始抱怨作用域聚合,这似乎在错误的方向上进行。
如果我使用 if
语句而不是 case
语句,也会发生同样的情况。
奇怪的地方来了。如果我的查询中有注释行(或者 last(SPLIT(a.category, "|")) as x
),查询将完美通过。
这是一个错误吗?我的查询看起来是正确的,并且在我的查询中有一个额外的列以某种方式让它通过是很奇怪的。
有没有比只保留不必要的列来稳定查询更好的方法来解决这个问题?
我认为使用 String functions 可以相对轻松地提取管道分隔字符串中的最后一个组件
同时,使用 Regular expression functions 的以下版本 - 对于可能更复杂的场景来说它更强大一些
SELECT
a.category AS category,
CASE
WHEN LENGTH(REGEXP_REPLACE(a.category, r"[^|]", "")) = 4
THEN REGEXP_EXTRACT(a.category, r'\|\w+\|\w+\|\w+\|(\w+)')
WHEN LENGTH(REGEXP_REPLACE(a.category, r"[^|]", "")) = 3
THEN REGEXP_EXTRACT(a.category, r'\|\w+\|\w+\|(\w+)')
WHEN LENGTH(REGEXP_REPLACE(a.category, r"[^|]", "")) = 2
THEN REGEXP_EXTRACT(a.category, r'\|\w+\|(\w+)')
ELSE NULL
END AS subcat1
FROM your_table a
没有分组,没有所问的不必要的列!
查询缺少 'WITHIN RECORD' 关键字。
SELECT
a.category AS category,
case
WHEN COUNT(SPLIT(a.category, "|")) = 4 then nth(4, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 3 then nth(2, SPLIT(a.category, "|"))
WHEN COUNT(SPLIT(a.category, "|")) = 2 then nth(2, SPLIT(a.category, "|"))
else null
end WITHIN RECORD as subcat1 ,
FROM (SELECT category FROM
(SELECT 'a|b|c' category), (SELECT 'a|b' category), (SELECT 'a|b|c|d' category)) a
请参阅 WITHIN 的文档:
WITHIN 关键字专门与聚合函数一起使用,以聚合记录和嵌套字段中的子字段和重复字段。当您指定 WITHIN 关键字时,您需要指定要聚合的范围 - WITHIN RECORD:聚合记录中重复值中的数据。