从每个 id 具有特定值的表中选择行

Posted

技术标签:

【中文标题】从每个 id 具有特定值的表中选择行【英文标题】:Selecting rows from a table with specific values per id 【发布时间】:2021-02-17 12:10:44 【问题描述】:

我有下表

表 1

Id   WFID  data1   data2
1    12    'd'     'e'
1    13    '3'     '4f'
1    15    'e'     'dd'
2    12    'f'     'ee'
3    17    'd'     'f'
2    17    'd'     'f'
4    12    'd'     'f'
5    20    'd'     'f'

从这个表中我只想选择只有 12 和 17 的行。就像从表中一样,我只想检索不同 id 的 2,3 和 4。1 被排除在外,因为它有 12,但也有 13 和 15。5 被排除在外,因为它有 20。

包含 2 个,因为它只有 12 个和 17 个。 3 被包括在内,因为它只有 17 个 4 被包括在内,因为它只有 12 个

【问题讨论】:

很乐意帮助您,但是您尝试过什么?你在哪里卡住了? 【参考方案1】:

如果您只想要满足条件的不同ids 的列表,您可以使用聚合和带有having 子句的过滤器:

select id
from mytable
group by id
having max(case when wfid not in (12, 17) then 1 else 0 end) = 0

这会过滤掉具有除1217 之外的任何wfid 的组。

如果你想要整个对应的行,那么窗口函数更合适:

select
from (
    select t.*,
        max(case when wfid not in (12, 17) then 1 else 0 end) over(partition by id) flag
    from mytable t
) t
where flag = 0

【讨论】:

【参考方案2】:

你真的需要从集合的角度开始思考。如果您提供可用于实验和演示的脚本,它对每个人都有帮助。这是使用 EXCEPT 运算符的另一种方法。这个想法是首先根据过滤器生成一组我们想要的 ID。然后生成一组我们不想要的 ID。使用 EXCEPT,我们可以从第一组中删除第二组。

declare @x table (Id tinyint, WFID tinyint, data1 char(1), data2 varchar(4));

insert @x (Id, WFID, data1, data2) values
(1,    12,    'd',     'e'),
(1,    13,    '3',     '4f'), 
(1,    15,    'e',     'dd'),
(2,    12,    'f',     'ee'),
(3,    17,    'd',     'f'),
(2,    17,    'd',     'f'),
(4,    12,    'd',     'f'),
(2,    12,    'z',     'ef'),
(5,    20,    'd',     'f');

select * from @x 
select id from @x where WFID not in (12, 17);

select id from @x where WFID  in (12, 17)
except
select id from @x where WFID not in (12, 17);

注意添加的行,以演示存在“重复”时会发生什么。

【讨论】:

非常感谢 SMor..下次我会确保我提供一个 playgroup 脚本..我尝试在 SQL Fiddle 中做一个,但即使我构建了架构,我仍然收到 Table not exist 的错误..下次我会更加努力的。

以上是关于从每个 id 具有特定值的表中选择行的主要内容,如果未能解决你的问题,请参考以下文章

从具有特定值的表中获取列名

从具有相同值的两个表中选择数据后结果重复

从 jsonb 数组包含具有特定属性的元素的表中选择

从列具有特定值的所有表中选择表名

SQL / Hive 选择具有特定列值的第一行

如何从1个表中选择许多行并将其插入另一个表中特定行的特定JSONB字段中?但是在单个原始SQL查询中