我有一个带有建筑物名称的表,例如A,B,C。这些建筑物名称可以重复。我还有另外一个专栏发言。例如第1层,第2层。同样,每个建筑物可能有多个第1层。第三列显示对象,例如电视,砖块,风扇。 我想检查建筑物与相应楼层的每种组合,例如A楼-1楼,A楼-2楼,如果存在对象“砖”,则必须存在“墙”。
示例数据: 对于每个建筑物和位置,如果存在“ WALL”,“ WINDOW”,“ WINDOW1”或“ WINDOW2”,则其他标志
BUILDING LOCATION OBJECT
A FLOOR1 WINDOW1
A FLOOR1 WINDOW
A FLOOR1 WINDOW2
A FLOOR2 WALL
B FLOOR1 WALL
C FLOOR1 WALL
C FLOOR1 WINDOW
期望的输出
BUILDING LOCATION ACTION
A FLOOR2 FLAG
B FLOOR1 FLAG
我尝试使用GROUP BY,DISTINCT,WHERE EXISTS,但是我似乎无法提出正确的逻辑。
答案 0 :(得分:1)
不存在:
select distinct t.building, t.location, 'FLAG' action
from tablename t
where object = 'WALL'
and not exists (
select 1 from tablename
where building = t.building and location = t.location
and object like 'WINDOW%'
)
请参见demo。
结果:
| building | location | action |
| -------- | -------- | ------ |
| A | FLOOR2 | FLAG |
| B | FLOOR1 | FLAG |
答案 1 :(得分:0)
SELECT building,
location,
MAX(CASE WHEN object = 'WALL' THEN 1 ELSE 0 END) as has_walls,
MAX(CASE WHEN object IN ('WINDOW', 'WINDOW1', 'WINDOW2') THEN 1 ELSE 0 END) as has_windows
FROM tablename
GROUP BY building, location
HAVING
has_walls <> has_windows;
因此,如果您有任何墙,MAX()
将返回1,与Windows相同。
这带来了WALL
不带WINDOWS
,但是也带来了WINDOWS
不带WALLS
让我知道您是否需要进一步提炼
如果您希望WALLS
不包含WINDOWS
SELECT building,
location,
MAX(CASE WHEN object = 'WALL' THEN 1 ELSE 0 END) as has_walls,
MAX(CASE WHEN object IN ('WINDOW', 'WINDOW1', 'WINDOW2') THEN 1 ELSE 0 END) as has_windows
FROM tablename
GROUP BY building, location
HAVING
has_walls > 0
AND has_windows = 0
答案 2 :(得分:0)
我实际上会以与forpas相同的方式编写查询。但这是另一种方式:
select BUILDING, LOCATION, 'FLAG' as `ACTION`
from my_table
group by BUILDING, LOCATION
having bit_or(OBJECT = 'WALL') -- at least one OBJECT is 'WALL'
and bit_and(OBJECT not rlike 'WINDOW[0-9]*') -- no OBJECT matches 'WINDOW[number]'
它比较短,但可能不容易理解。