查询数据库以获取不同的值并根据条件聚合数据
Query database for distinct values and aggregate data based on condition
我正在尝试从 Postgres 数据库中提取不同的项目,根据条件将 table 中的列与另一个 table 中的列配对。简化版如下所示:
CREATE TABLE users
(
id SERIAL PRIMARY KEY,
name VARCHAR(255)
);
CREATE TABLE photos
(
id INT PRIMARY KEY,
user_id INTEGER REFERENCES users(id),
flag VARCHAR(255)
);
INSERT INTO users VALUES (1, 'Bob');
INSERT INTO users VALUES (2, 'Alice');
INSERT INTO users VALUES (3, 'John');
INSERT INTO photos VALUES (1001, 1, 'a');
INSERT INTO photos VALUES (1002, 1, 'b');
INSERT INTO photos VALUES (1003, 1, 'c');
INSERT INTO photos VALUES (1004, 2, 'a');
INSERT INTO photos VALUES (1004, 2, 'x');
我需要的是提取每个用户名,只提取一次,并为每个用户名提取一个标志值。标志值应该优先考虑一个特定的值,比方说 b
。所以,结果应该是这样的:
Bob b
Alice a
其中 Bob
拥有带有 b
标记的照片,而 Alice
没有并且 John
没有照片。对于 Alice
,标志值的输出并不重要(a
或 x
一样好)只要她没有被标记的照片 b
.
我发现的最接近的东西是一些自连接查询,其中标志值将使用 min()
或 max()
聚合,但我正在寻找一个特定的值,这不是第一个,也不是最后。此外,我发现您可以定义自己的聚合函数,但我想知道是否有更简单的方法来调节查询以获得所需的数据。
谢谢!
这是一个聚合方法:
select u.name,
coalesce(max(flag) filter (where flag = 'b'),
min(flag)
) as flag
from users u left join
photos p
on u.id = p.user_id
group by u.id, u.name;
也就是说,更典型的方法是优先查询。也许:
select distinct on (u.id) u.name, p.flag
from users u left join
photos p
on u.id = p.user_id
order by u.id, (p.flag = 'b') desc;
我正在尝试从 Postgres 数据库中提取不同的项目,根据条件将 table 中的列与另一个 table 中的列配对。简化版如下所示:
CREATE TABLE users
(
id SERIAL PRIMARY KEY,
name VARCHAR(255)
);
CREATE TABLE photos
(
id INT PRIMARY KEY,
user_id INTEGER REFERENCES users(id),
flag VARCHAR(255)
);
INSERT INTO users VALUES (1, 'Bob');
INSERT INTO users VALUES (2, 'Alice');
INSERT INTO users VALUES (3, 'John');
INSERT INTO photos VALUES (1001, 1, 'a');
INSERT INTO photos VALUES (1002, 1, 'b');
INSERT INTO photos VALUES (1003, 1, 'c');
INSERT INTO photos VALUES (1004, 2, 'a');
INSERT INTO photos VALUES (1004, 2, 'x');
我需要的是提取每个用户名,只提取一次,并为每个用户名提取一个标志值。标志值应该优先考虑一个特定的值,比方说 b
。所以,结果应该是这样的:
Bob b
Alice a
其中 Bob
拥有带有 b
标记的照片,而 Alice
没有并且 John
没有照片。对于 Alice
,标志值的输出并不重要(a
或 x
一样好)只要她没有被标记的照片 b
.
我发现的最接近的东西是一些自连接查询,其中标志值将使用 min()
或 max()
聚合,但我正在寻找一个特定的值,这不是第一个,也不是最后。此外,我发现您可以定义自己的聚合函数,但我想知道是否有更简单的方法来调节查询以获得所需的数据。
谢谢!
这是一个聚合方法:
select u.name,
coalesce(max(flag) filter (where flag = 'b'),
min(flag)
) as flag
from users u left join
photos p
on u.id = p.user_id
group by u.id, u.name;
也就是说,更典型的方法是优先查询。也许:
select distinct on (u.id) u.name, p.flag
from users u left join
photos p
on u.id = p.user_id
order by u.id, (p.flag = 'b') desc;