SQL实现:按Serial#分组,判断Data列是否全为特定值并标记
问题描述
现有一张SQL表,包含Serial#(序列号)和Data(数据)列。需求为:针对每个Serial#,判断其对应的所有Data列值是否全部等于指定的特定值(如示例中的pass),满足则标记为1,否则标记为0。
示例数据
| Serial# | Data |
|---|---|
| 1 | pass |
| 1 | pass |
| 2 | pass |
| 2 | fail |
| 3 | fail |
| 3 | fail |
| 3 | fail |
预期结果
| Serial# | IsAllPass |
|---|---|
| 1 | 1 |
| 2 | 0 |
| 3 | 0 |
解决方案
以下是几种通用的SQL实现方式,适用于MySQL、PostgreSQL、SQL Server等主流数据库:
方法1:通过统计匹配数与总记录数对比
统计每个分组中符合目标值的记录数,和分组总记录数做比较,相等则说明所有数据都匹配目标值:
SELECT `Serial#`, CASE WHEN COUNT(*) = COUNT(CASE WHEN Data = 'pass' THEN 1 END) THEN 1 ELSE 0 END AS IsAllPass FROM your_table_name GROUP BY `Serial#`;
- 逻辑说明:
COUNT(CASE WHEN Data = 'pass' THEN 1 END)仅统计Data为pass的记录数,若和分组总记录数COUNT(*)相等,即可判定该组所有数据都是pass。
方法2:利用MAX/MIN值判断
如果分组内所有Data都等于目标值,那么该组的MAX和MIN值都会等于目标值:
SELECT `Serial#`, CASE WHEN MAX(Data) = 'pass' AND MIN(Data) = 'pass' THEN 1 ELSE 0 END AS IsAllPass FROM your_table_name GROUP BY `Serial#`;
- 逻辑说明:只要分组中有一个值不等于
pass,MAX或MIN就会偏离pass,从而标记为0。
方法3:通过子查询检查是否存在不匹配记录
判断每个分组下是否存在不等于目标值的记录,不存在则标记为1:
SELECT DISTINCT t1.`Serial#`, CASE WHEN NOT EXISTS ( SELECT 1 FROM your_table_name t2 WHERE t2.`Serial#` = t1.`Serial#` AND t2.Data != 'pass' ) THEN 1 ELSE 0 END AS IsAllPass FROM your_table_name t1;
- 逻辑说明:子查询会查找当前
Serial#下是否有非pass的记录,无匹配结果则说明该组全是pass。
内容的提问来源于stack exchange,提问作者user2059972
相关产品推荐
相关产品推荐

