AI已经进化到随便写SQL了吗? AI已经进化到给表结构,给业务报表,给业务逻辑,sql语句轻松生成的地步了吗?
总结:需要循序简介把问题描述清楚,才能帮你解决, 想要一步解决复杂问题几乎不太可能,AI有一个学习过程,逐步地理解你想要的业务逻辑。以上还只是单表的复杂查询,多表复杂查询还没测试。
标红部分为提问内容
文章目录
第一篇
甚至帮你建表
CREATE TABLE performance_table (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(32) COMMENT '姓名',
score INT COMMENT '分数',
check_in_times INT COMMENT '签到次数'
) COMMENT='业绩签到统计';
甚至帮你造数据
INSERT INTO performance_table (name, score, check_in_times) VALUES
('张三', 85, 17),
('李四', 92, 14),
('王五', 76, 23),
('赵六', 88, 19),
('孙七', 95, 11),
('周八', 80, 21),
('吴九', 89, 15),
('郑十', 73, 10),
('冯十一', 90, 25),
('陈十二', 84, 18),
('褚十三', 78, 16),
('卫十四', 97, 22),
('蒋十五', 82, 13),
('沈十六', 86, 12),
('韩十七', 74, 20),
('杨十八', 93, 9),
('朱十九', 87, 24),
('秦二十', 79, 8),
('尤二十一', 91, 10),
('许二十二', 83, 25);
根据所给表结构和业务逻辑,金银牌争夺结果如下
甚至帮你实现业务逻辑
业绩大于30,签到大于10次参与排名,1-3名且签到次数大于20获得金牌,3-7名且签到次数大于15获得银牌,8-14获得铜牌,按最大能满足的条件给予奖项,但不能占用每个奖项名额,如果奖项名额满了,向下递补, 且金牌名额3个,银牌名额4个,铜牌名额6个, 使用mysql写一个sql实现以上业务逻辑。
为了实现你所描述的业务逻辑,我们需要构造一个多步骤的SQL查询。这个查询首先会筛选出符合条件(业绩大于30且签到次数大于10次)的记录,然后根据设定的条件分配奖项,同时确保每个奖项的名额限制。实现方案
- 初步筛选:从 performance_table 表中选出所有满足业绩大于30和签到次数大于10次的记录。
- 排名计算:基于业绩分数进行排名,并为每个候选人标记可能获得的最高奖项。
- 分配奖项:按照规则分配金牌、银牌、铜牌,确保不超出各奖项的名额限制,并处理递补逻辑。
- 最终结果输出:展示获奖名单及其对应的奖项。
以下是实现该逻辑的MySQL代码:
WITH ranked_performance AS (
SELECT
name,
score,
check_in_times,
ROW_NUMBER() OVER (ORDER BY score DESC, check_in_times DESC) AS rank
FROM performance_table
WHERE score > 30 AND check_in_times > 10
),
awarded_performance AS (
SELECT
name,
score,
check_in_times,
CASE
WHEN rank <= 3 AND check_in_times > 20 THEN '金牌'
WHEN rank <= 7 AND check_in_times > 15 THEN '银牌'
WHEN rank <= 14 THEN '铜牌'
ELSE NULL
END AS award,
rank
FROM ranked_performance
),
gold_awards AS (
SELECT
name,
score,
check_in_times,
'金牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '金牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM awarded_performance
WHERE award = '金牌'
LIMIT 3
),
silver_awards AS (
SELECT
name,
score,
check_in_times,
'银牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '银牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM awarded_performance
WHERE award = '银牌'
LIMIT 4
),
bronze_awards AS (
SELECT
name,
score,
check_in_times,
'铜牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '铜牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM awarded_performance
WHERE award = '铜牌'
LIMIT 6
),
all_awards AS (
SELECT * FROM gold_awards
UNION ALL
SELECT * FROM silver_awards
UNION ALL
SELECT * FROM bronze_awards
),
remaining_candidates AS (
SELECT
name,
score,
check_in_times,
rank
FROM awarded_performance
WHERE name NOT IN (SELECT name FROM all_awards)
),
final_adjustments AS (
SELECT
name,
score,
check_in_times,
'银牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '银牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM remaining_candidates
WHERE check_in_times > 15
LIMIT 4 - (SELECT COUNT(*) FROM silver_awards)
UNION ALL
SELECT
name,
score,
check_in_times,
'铜牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '铜牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM remaining_candidates
WHERE check_in_times <= 15
LIMIT 6 - (SELECT COUNT(*) FROM bronze_awards)
)
SELECT
name,
score,
check_in_times,
COALESCE(final_award, '未获奖') AS final_award
FROM (
SELECT * FROM all_awards
UNION ALL
SELECT * FROM final_adjustments
) t
ORDER BY FIELD(final_award, '金牌', '银牌', '铜牌'), score DESC, check_in_times DESC;
这段SQL语句通过使用CTE(Common Table Expressions)逐步构建了你需要的逻辑。它首先筛选并排名,然后按顺序分配各个奖项,最后处理剩余候选人的递补逻辑。这样可以确保每个奖项的名额限制得到遵守,同时尽可能多地奖励参与者。如果有任何调整或更具体的表结构信息,请告诉我,以便进一步优化此查询!
rank 是个关键字不能作为别名
理解了,我们可以调整查询以避免使用 rank 作为别名。下面是更新后的SQL查询:
WITH ranked_performance AS (
SELECT
name,
score,
check_in_times,
ROW_NUMBER() OVER (ORDER BY score DESC, check_in_times DESC) AS row_num
FROM performance_table
WHERE score > 30 AND check_in_times > 10
),
awarded_performance AS (
SELECT
name,
score,
check_in_times,
CASE
WHEN row_num <= 3 AND check_in_times > 20 THEN '金牌'
WHEN row_num <= 7 AND check_in_times > 15 THEN '银牌'
WHEN row_num <= 14 THEN '铜牌'
ELSE NULL
END AS award,
row_num
FROM ranked_performance
),
gold_awards AS (
SELECT
name,
score,
check_in_times,
'金牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '金牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM awarded_performance
WHERE award = '金牌'
LIMIT 3
),
silver_awards AS (
SELECT
name,
score,
check_in_times,
'银牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '银牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM awarded_performance
WHERE award = '银牌'
LIMIT 4
),
bronze_awards AS (
SELECT
name,
score,
check_in_times,
'铜牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '铜牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM awarded_performance
WHERE award = '铜牌'
LIMIT 6
),
all_awards AS (
SELECT * FROM gold_awards
UNION ALL
SELECT * FROM silver_awards
UNION ALL
SELECT * FROM bronze_awards
),
remaining_candidates AS (
SELECT
name,
score,
check_in_times,
row_num
FROM awarded_performance
WHERE name NOT IN (SELECT name FROM all_awards)
),
final_adjustments AS (
SELECT
name,
score,
check_in_times,
'银牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '银牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM remaining_candidates
WHERE check_in_times > 15
LIMIT 4 - (SELECT COUNT(*) FROM silver_awards)
UNION ALL
SELECT
name,
score,
check_in_times,
'铜牌' AS final_award,
ROW_NUMBER() OVER (PARTITION BY '铜牌' ORDER BY score DESC, check_in_times DESC) AS award_rank
FROM remaining_candidates
WHERE check_in_times <= 15
LIMIT 6 - (SELECT COUNT(*) FROM bronze_awards)
)
SELECT
name,
score,
check_in_times,
COALESCE(final_award, '未获奖') AS final_award
FROM