【发布时间】:2017-07-04 20:37:39
【问题描述】:
使用 Postgres 我有 3 个表:
CREATE TABLE post (id SERIAL, body TEXT);
CREATE TABLE tag (id SERIAL, name TEXT);
CREATE TABLE post_tag (post_id INT, tag_id INT);
INSERT INTO post(body) values('post 1');
INSERT INTO post(body) values('post 2');
INSERT INTO tag(name) values('a');
INSERT INTO tag(name) values('b');
INSERT INTO post_tag values(1, 1);
INSERT INTO post_tag values(1, 2);
INSERT INTO post_tag values(2, 1);
因此post 1 有标签a, b 和post 2 有a 作为标签。
问题:如何选择所有没有标签b的帖子,这意味着它应该只选择post 2。
这里的查询不好,因为它会选择两个帖子,因为 post 1 有 2 个标签 a 和 b:
SELECT post.*
FROM post
JOIN post_tag ON post_tag.post_id = post.id
JOIN tag ON tag.id = post_tag.tag_id
WHERE tag.name != 'b';
下面的查询有效,但错误,因为如果有标签aaaaaaab,那么它也会匹配它:
SELECT post.id, post.body, string_agg(tag1.name, ', ')
FROM post
JOIN post_tag ON post_tag.post_id = post.id
JOIN tag ON tag.id = post_tag.tag_id
GROUP BY post.id, post.body
HAVING string_agg(tag.name, ', ') not like '%b, %';
我正在寻找一种“正确”且有效的方法。
编辑:查询还应该匹配根本没有任何标签的帖子。
【问题讨论】:
标签: postgresql