英文:
Trying to pluck row values and display as column values with multiple where clauses in MySQL
问题
我有以下查询:
SELECT id, user_uid, charity_id, value FROM donations
WHERE charity_id IN (178, 25, 209, 150, 176)
AND year = 2022
ORDER BY value DESC
它输出以下表格:
id | user_uid | charity_id | value |
---|---|---|---|
267558 | 1a36d6c1-3eca-4a23-a3c7-2827acca3397 | 178 | 905 |
267552 | 1a36d6c1-3eca-4a23-a3c7-2827acca3397 | 25 | 630 |
92944 | 03661b7a-56d0-43e1-9d5e-3f913cf8fefd | 178 | 575 |
... | |||
271876 | a620d031-c947-4513-b307-7bafb526789a | 150 | 305 |
95444 | 03661b7a-56d0-43e1-9d5e-3f913cf8fefd | 176 | 300 |
但我想以以下格式输出:
user_uid | charity_178 | charity_25 | charity_209 | charity_150 | charity_176 |
---|---|---|---|---|---|
1a36d6c1-3eca-4a23-a3c7-2827acca3397 | 905 | 630 | NULL | NULL | NULL |
03661b7a-56d0-43e1-9d5e-3f913cf8fefd | 575 | NULL | NULL | NULL | 300 |
... | |||||
a620d031-c947-4513-b307-7bafb526789a | NULL | NULL | NULL | 305 | NULL |
我尝试了以下代码,我认为它应该可以工作...
SELECT
fun.uid,
d1.value AS 'charity_178',
d2.value AS 'charity_209',
d3.value AS 'charity_25',
d4.value AS 'charity_150',
d5.value AS 'charity_176'
FROM `fundraisers` AS fun
LEFT JOIN `donations` AS d1 ON fun.uid = d1.user_uid AND d1.charity_id = 178 AND d1.year = 2022
LEFT JOIN `donations` AS d2 ON fun.uid = d2.user_uid AND d2.charity_id = 209 AND d2.year = 2022
LEFT JOIN `donations` AS d3 ON fun.uid = d3.user_uid AND d3.charity_id = 25 AND d3.year = 2022
LEFT JOIN `donations` AS d4 ON fun.uid = d4.user_uid AND d4.charity_id = 150 AND d4.year = 2022
LEFT JOIN `donations` AS d5 ON fun.uid = d5.user_uid AND d5.charity_id = 176 AND d5.year = 2022
但它没有连接到在donations
表中缺失或为空的任何内容。
所以只返回像这样的结果:
user_uid | charity_178 | charity_25 | charity_209 | charity_150 | charity_176 |
---|---|---|---|---|---|
2cd3f974-4cc4-4b89-9bad-475321b68c83 | 200 | 10 | 100 | 340 | 90 |
有很多用户缺失。
顺便说一句,我实际上是在Laravel应用程序中进行这个操作,但数据集很大,尝试在这种格式下操作集合会导致服务器负载过重,所以我尝试将工作转移到数据库中,并使用动态创建的SQL字符串和DB::RAW($sql)
使用DB门面。
英文:
I have the following query:
SELECT id, user_uid, charity_id, value FROM donations
WHERE charity_id IN (178, 25, 209, 150, 176)
AND year = 2022
ORDER BY value DESC
Which outputs the following table:
id | user_uid | charity_id | value |
---|---|---|---|
267558 | 1a36d6c1-3eca-4a23-a3c7-2827acca3397 | 178 | 905 |
267552 | 1a36d6c1-3eca-4a23-a3c7-2827acca3397 | 25 | 630 |
92944 | 03661b7a-56d0-43e1-9d5e-3f913cf8fefd | 178 | 575 |
... | |||
271876 | a620d031-c947-4513-b307-7bafb526789a | 150 | 305 |
95444 | 03661b7a-56d0-43e1-9d5e-3f913cf8fefd | 176 | 300 |
But I'm trying to output it in the following format:
user_uid | charity_178 | charity_25 | charity_209 | charity_150 | charity_176 |
---|---|---|---|---|---|
1a36d6c1-3eca-4a23-a3c7-2827acca3397 | 905 | 630 | NULL | NULL | NULL |
03661b7a-56d0-43e1-9d5e-3f913cf8fefd | 575 | NULL | NULL | NULL | 300 |
... | |||||
a620d031-c947-4513-b307-7bafb526789a | NULL | 30 | NULL | 305 | NULL |
I've tried the following, which I thought should work...
SELECT
fun.uid,
d1.value AS 'charity_178',
d2.value AS 'charity_209',
d3.value AS 'charity_25',
d4.value AS 'charity_150',
d5.value AS 'charity_176'
FROM `fundraisers` AS fun
JOIN `donations` AS d1 ON fun.uid = d1.user_uid
JOIN `donations` AS d2 ON fun.uid = d2.user_uid
JOIN `donations` AS d3 ON fun.uid = d3.user_uid
JOIN `donations` AS d4 ON fun.uid = d4.user_uid
JOIN `donations` AS d5 ON fun.uid = d5.user_uid
WHERE d1.year = 2022
AND d1.charity = 178
AND d2.year = 2022
AND d2.charity = 209
AND d3.year = 2022
AND d3.charity = 25
AND d4.year = 2022
AND d4.charity = 150
AND d5.year = 2022
AND d5.charity = 176
But it isn't joining anything that is missing or null in the donations
table.
So only returns something like this:
user_uid | charity_178 | charity_25 | charity_209 | charity_150 | charity_176 |
---|---|---|---|---|---|
2cd3f974-4cc4-4b89-9bad-475321b68c83 | 200 | 10 | 100 | 340 | 90 |
With a lot of users missing.
FWIW, I'm actually doing this in a Laravel application, but the dataset is large and trying to manipulate a collection in this format is killing the server, so I'm trying to move the work to the database and using the DB facade with a dynamically created sql string and DB::RAW($sql)
答案1
得分: 1
根据@user1191247提供的问题/答案,我可以使用条件聚合。
以下代码在我的示例中有效:
SELECT user_uid,
MAX(CASE WHEN charity_id = 178 THEN value END) AS "charity_178",
MAX(CASE WHEN charity_id = 209 THEN value END) AS "charity_209",
MAX(CASE WHEN charity_id = 25 THEN value END) AS "charity_25",
MAX(CASE WHEN charity_id = 150 THEN value END) AS "charity_150",
MAX(CASE WHEN charity_id = 176 THEN value END) AS "charity_176"
FROM donations
GROUP BY user_uid;
英文:
From the question/answer suggested by @user1191247, I can use conditional aggregation.
The following code works in my example:
SELECT user_uid,
MAX(CASE WHEN charity_id = 178 THEN value END) "charity_178",
MAX(CASE WHEN charity_id = 209 THEN value END) "charity_209",
MAX(CASE WHEN charity_id = 25 THEN value END) "charity_25",
MAX(CASE WHEN charity_id = 150 THEN value END) "charity_150",
MAX(CASE WHEN charity_id = 176 THEN value END) "charity_176"
FROM donations
GROUP BY user_uid;
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论