我有一个名为test的下表,并且只想将其选择到相同id的第一个删除语句('1144QQT')上方的行。因此,从2021-03-01到2021-06-02(只有粗体)。因此,这将排除带有delete语句的行。它确实包括更多不同类型的id和更多相同类型的id。
表模式:
CREATE TABLE test(
id BIGINT PRIMARY KEY NOT NULL,
barcode_id VARCHAR NOT NULL,
date DATE NOT NULL,
keyword VARCHAR NOT NULL
);
INSERT INTO test
VALUES
(1, '1144QQT', '2021-03-01'::date, 'insert'),
(2, '1144QQT', '2021-03-01'::date, 'insert'),
(3, '1144QQT', '2021-03-01'::date, 'insert'),
(4, '1144QQT', '2021-03-01'::date, 'insert'),
(5, '1144QQT', '2021-03-01'::date, 'insert'),
(6, '1144QQT', '2021-03-01'::date, 'insert'),
(7, '1144QQT', '2021-03-01'::date, 'insert'),
(8, '1144QQT', '2021-03-01'::date, 'insert'),
(9, '1144QQT', '2021-03-01'::date, 'insert'),
(10, '1144QQT', '2021-03-01'::date, 'insert'),
(11, '1144QQT', '2021-03-01'::date, 'insert');
id | barcode_id | 日期 | >关键字 | ||
---|---|---|---|---|---|
1 | 11144QQT | strong>2021-03-01||||
2 | 11144QQT | td style="text align:left;">611144QQT021-03-06 | >调整 | ||
7 | 1144QQT | 2021-03-07 | 删除|||
8 | 11144QQT | 2021-03-08 | 入[/tr>2021-03-09调整|||
10 | 11144QQT | 11 | 4477aTT | 2021-03-11 | 除[/tr>
根据您的描述,这个逻辑似乎可以满足您的要求:
select t.*
from t
where t.id = '1144QQT' and t.keyword <> 'delete';
这就假设在删除之后没有id的行,但这似乎是合理的,并且与您的示例数据一致。
对于您的特定问题,有一种方法是关联子查询:
select t.*
from t
where t.id = '1144QQT' and
t.id < (select min(t2.date)
from t t2
where t2.id = t.id and
t2.keyword <> 'delete'
);
上述版本要求存在一个";删除"--根据你的问题,目前还不清楚这是否是一项要求。另一种选择使用窗口功能:
select t.*
from (select t.*,
min(date) filter (where keyword = 'delete') over (partition by id) as min_delete_date
where t.id = '1144QQT'
) t
where date < min_delete_date;
如果你想要所有的行,如果没有";删除";,则将CCD_ 1添加到外部CCD_。
使用SUM()
窗口函数用keyword = 'delete'
:识别第一行之前的行
SELECT id, date, keyword
FROM (
SELECT *, SUM((keyword = 'delete')::int) OVER (ORDER BY date) grp
FROM tablename
WHERE id = '1144QQT'
) t
WHERE grp = 0
请参阅演示
结果:
我只想把它选到同一id的第一条删除语句上方的一行。
NOT EXISTS()
拯救:(注意date
是保留字,是列的坏名称)
SELECT *
FROM ztable zt
WHERE zt.zid = '1144QQT'
AND NOT EXISTS (
SELECT * FROM ztable nx
WHERE nx.zid = zt.zid
AND nx.zkeyword = 'delete'
AND nx.zdate <= zt.zdate
);