我正在尝试执行一个相当复杂的(至少对我而言)查询,该查询涉及获取可能具有NULL
值的行。
此处有四个表格,tags
,questions_tags
,users_experience
和answers
。这种联系非常简单。问题被标记,标签具有名称,用户给出问题的答案,用户具有特定标签的经验。我想找到用户给出的答案,以及他们对这些问题标签的体验(可能是NULL
)。我按照给定特定标签的答案数量排序。
我的查询如下。这根本没有优化(如果你有优化建议,请建议远离!):
SELECT t.tag_id, t.name, ue.body, COUNT(a.qid)
FROM tags AS t
LEFT JOIN users_experience AS ue
ON t.tag_id = ue.tag_id
LEFT JOIN questions_tags AS qt
ON qt.tag_id = t.tag_id
LEFT JOIN answers AS a
ON a.qid = qt.qid
WHERE a.uid=1
GROUP BY t.tag_id
ORDER BY COUNT(a.qid) DESC;
我遇到上述问题时遇到的问题是,如果任何人已经注意到某个特定代码的体验,那么这将显示给用户是否是他们的体验。我只想看到特定用户的体验,这个查询只是没有做到。我在其他地方遇到过这个问题并且被困住了,所以不得不乱砍它。
我尝试将AND ue.uid = 1
添加到查询中,但这会将结果仅限于已经提供体验的结果,并且不会返回我想要的NULL
值。
有关该怎么做的任何想法?
答案 0 :(得分:2)
您的AND ue.uid = 1
本能没有错,但它属于ON
子句,因此它是JOIN
的一部分,并且用于确定哪些行有资格加入。
LEFT JOIN users_experience AS ue
ON t.tag_id = ue.tag_id AND ue.uid = a.uid
(然后该联接应放在answers
联接下。)
答案 1 :(得分:0)
我认为您需要包含用户的表格。通过用户表中的uid(保证在哪里)进行过滤,这应该可以为您提供所需的内容。 (包括空值)。我不确切知道你的用户表是什么样的,但我假设你的查询是这样的:
SELECT t.tag_id, t.name, ue.body, COUNT(a.qid)
FROM users
LEFT JOIN users_experience AS ue
ON users.uid = ue.uid
LEFT JOIN tags
ON t.tag_id = ue.tag_id
LEFT JOIN questions_tags AS qt
ON qt.tag_id = t.tag_id
LEFT JOIN answers AS a
ON a.qid = qt.qid
WHERE users.uid=1
GROUP BY t.tag_id
ORDER BY COUNT(a.qid) DESC;
至于优化 - LEFT JOIN
通常被认为是坏的,除非这些表非常小。 MySQL基本上必须在整个表中搜索NULL
值。实际上,检查您的用户是否首先在左连接表中有任何记录并且仅在您找到记录时仅使用常规JOIN
发出第二个查询可能会更快。
希望有所帮助!