Postgresql ECORD顺序正确(每个开始模式都有一个匹配的停止模式,并且它们不嵌套) |action id | comment | timestamp | |----------|-----------------|--------------|
ECORD顺序正确(每个开始模式都有一个匹配的停止模式,并且它们不嵌套)Postgresql ECORD顺序正确(每个开始模式都有一个匹配的停止模式,并且它们不嵌套) |action id | comment | timestamp | |----------|-----------------|--------------|,postgresql,Postgresql,ECORD顺序正确(每个开始模式都有一个匹配的停止模式,并且它们不嵌套) |action id | comment | timestamp | |----------|-----------------|--------------| | 0110 | random comment | timestamp 1 | | 0117 | text pattern 1 | timestamp 2 | | 0129 | RANDOM COMMENT
|action id | comment | timestamp |
|----------|-----------------|--------------|
| 0110 | random comment | timestamp 1 |
| 0117 | text pattern 1 | timestamp 2 |
| 0129 | RANDOM COMMENT | timestamp 3 |
| 0130 | text pattern 2 | timestamp 4 |
| 0136 | random comment | timestamp 5 |
| etc.. | | |
select distinct ht.accountid, ht.id, ht.comment
from historic_table ht
where ht.id > (select MAX(ht1.id) from historic_table ht1 where ht1.accountid = ht.accountid and ht1.comment ilike '%comment pattern 1%')
and ht.id < (select MAX(ht2.id) from historic_table ht2 where ht2.accountid = ht.accountid and ht2.comment ilike '%comment pattern 2%')
limit 10
CREATE TABLE zaction(
id INTEGER NOT NULL PRIMARY KEY
, zcomment text
, ztimestamp timestamp NOT NULL
);
INSERT INTO zaction(id, zcomment, ztimestamp) VALUES
( 0110, 'random comment', '2017-04-27 12:00:00' )
,( 0117, 'text pattern 1', '2017-04-27 12:10:00' )
,( 0129, 'RANDOM COMMENT', '2017-04-27 12:20:00' )
,( 0130, 'text pattern 2', '2017-04-27 12:30:00' )
,( 0136, 'random comment', '2017-04-27 12:40:00' )
--
,( 1110, 'random comment', '2017-04-27 12:00:00' )
,( 1117, 'text pattern 1', '2017-04-27 12:10:00' )
,( 1123, 'RANDOM COMMENT', '2017-04-27 12:20:00' )
,( 1129, 'RANDOM CONTENT', '2017-04-27 12:20:00' )
,( 1130, 'text pattern 2', '2017-04-27 12:30:00' )
,( 1136, 'random comment', '2017-04-27 12:40:00' )
--
;
VACUUM ANALYZE zaction;
-- SELECT * FROM zaction;
EXPLAIN
WITH z1 AS (
SELECT za.id
, CASE WHEN zcomment ilike '%text pattern 1' THEN 1
WHEN zcomment ilike '%text pattern 2' THEN -1
ELSE 0 END AS dir
FROM zaction za
)
, z2 AS (
SELECT z1.id, z1.dir
, SUM(z1.dir) OVER (ORDER BY z1.id) AS yesno
FROM z1
)
SELECT za.*
FROM zaction za
JOIN z2 ON z2.id = za.id AND z2.yesno > 0 AND z2.dir = 0
;
-- EXPLAIN
WITH z1 AS (
SELECT za.id
, CASE WHEN zcomment ilike '%text pattern 1' THEN 1
WHEN zcomment ilike '%text pattern 2' THEN -1
ELSE 0 END AS dir
FROM zaction za
WHERE zcomment ilike '%text pattern %' -- <<== preselection to keep the CTE small
)
SELECT za.*
FROM zaction za
JOIN ( -- <<== Join with subquery to give the optimiser some freedom
SELECT za.id, z1.dir
, SUM(z1.dir) OVER (ORDER BY za.id) AS yesno
FROM zaction za
LEFT JOIN z1 ON z1.id = za.id -- <<== remerge with original set, whicha coulduse an index
) z2 ON z2.id = za.id AND z2.yesno > 0 AND z2.dir IS DISTINCT FROM 1
;
select ht.accountid
,string_agg(ht.id::text, ', ') as actions_ids
,string_agg(ht.comment, ', ') as comments
from historic_table ht
where ht.timestamp >= '2017-02-01'
and ht.timestamp < '2017-03-01'
and ht.id > (select max(ht1.id) from historic_table ht1 where ht1.accountid = ht.accountid and ht1.comment ilike '%comment pattern 1%')
and ht.id < (select max(ht2.id) from historic_table ht2 where ht2.accountid = ht.accountid and ht2.comment ilike '%comment pattern 2%')
group by ht.accountid
order by 1