数据集: SOTorrent-这是数据集(托管在Google的BigQuery上):您可以在此处运行查询。它有一个Posts表。尽管我试图解释以下相关字段,但仍可以在此处找到帖子表的详细架构,以供您参考:SO Schema
SO:StackOverflow
背景:数据集有一个名为帖子的表格。在该表中,存在一个字段 PostTypeId :
如果该字段为1,则表示我们正在查看的帖子是在SO上发布的问题。在这种情况下,另一个名为 Tags 的字段将包含问题的OP在SO上分配的标签。
如果该字段为2,则为在SO上发布的答案。在这种情况下,标签字段将为空。
问题:仅选择那些已附加Android标签的线程的所有答案。
我的解决方案:
SELECT
p.Id,
p.Score,
p.body
FROM
[sotorrent-org:2018_09_23.Posts] p
WHERE
p.Tags LIKE "%android%"
AND p.PostTypeId = 2
LIMIT
10
但是,很明显,上面的查询将返回null
,因为WHERE子句检查不能共存的条件。如果帖子带有标签,则不能作为答案。如果是答案,则不能包含标签。
如何解决此问题并在同一张表上检查两个互斥条件?
答案 0 :(得分:3)
您需要使用ParentId
字段将posts表与其自身相连:
#standardSQL
SELECT
answer.Id
, answer.Score
, answer.body
FROM
`sotorrent-org.2018_09_23.Posts` question
JOIN
`sotorrent-org.2018_09_23.Posts` answer
ON
answer.ParentId=question.Id
AND answer.PostTypeId=2
AND question.PostTypeId=1
WHERE
question.Tags LIKE "%android%"
AND question.PostTypeId = 1
AND answer.PostTypeId = 2
LIMIT
10
答案 1 :(得分:0)
如果我理解正确,我认为最好的方法是窗口函数:
SELECT p.Id, p.Score p.body
FROM (SELECT p.*,
MAX(p.tags) OVER (PARTITION BY COALESCE(p.parentid, p.id)) as tags
FROM `sotorrent-org.2018_09_23.Posts` p
)
WHERE p.Tags LIKE '%android%' AND
p.PostTypeId = 2
LIMIT 10;
这应该更快。