所以我有一个跟踪项目状态更新的表。现在,每次项目更改状态时,都会将其记录插入到新行中。该表的简化形式如下所示:
+-----------+------------+--------+
| ProjectID | UpdateDate | Status |
+-----------+------------+--------+
| | | |
| | | |
| | | |
+-----------+------------+--------+
Status
列的可能值为:
现在这里至少对我来说很棘手。我希望能够只选择当前重新激活的项目。这在逻辑上意味着一个项目具有已重新激活的现有行作为其状态,但没有将该ID的最新记录作为已关闭状态。感谢您对此的任何帮助,我很难为此查看SQL查询。
BONUS (对我来说)
如果您可以将查询编写为一个非常棒的创建存储过程。
更新
强调重新激活的要求。
更新更新
一些测试数据
ProjectID | UpdateDate | Status
-----------------------------------
3566 | 2011-11-09 | Pending
1282 | 2011-11-17 | Reactivated
3351 | 2011-11-17 | Closed
2252 | 2011-11-17 | Reactivated
2252 | 2011-11-17 | Active
现在有了这个查询,它应该显示id的1282和2252,因为它们都已连续重新激活,并且没有作为最后更新状态关闭。
答案 0 :(得分:1)
这是“最近重新激活”
select
*
from
Project P -- I'm guessing at this table name
join
(select MAX(UpdateDate) lastUpdate, ProjectId from Project group by ProjectId) L on L.ProjectId = P.ProjectId AND L.lastUpdate = P.UpdateDate
where
Status = 'Reactivated'
这是“最近没有关闭,但在某些时候已被重新激活”,这就是你要求的
select distinct -- there may be more than one "reactivated" per project
R.ProjectId
from
Project R join
(select
P.ProjectId
from
Project P join
(select
MAX(InsertDate) InsertDate,
ProjectId
from
Project
group by
ProjectId) MostRecent M on P.InsertDate = M.InsertDate and P.ProjectId = M.ProjectId
where
Status <> 'Closed') O on O.ProjectId = R.ProjectId
where
Status = 'Reactivated'
答案 1 :(得分:0)
选择所有重新激活的项目并检查它是否处于关闭状态。
它没有优化,但我认为它有效。
SELECT p1.*
FROM project as p1
WHERE Status = "Reactivated"
AND ProjectID NOT IN (SELECT ProjectID FROM project AS p2 WHERE Status = "Closed" AND p2.Updatedate > p1.UpdateDate)
|-ProjectID-|-UpdateDate-|- Status -|
|- 1 -|-2011-11-15-|- Closed -|
|- 1 -|-2011-11-16-|- Reactivated -|
|- 1 -|-2011-11-17-|- Opened -|
|- 2 -|-2011-11-15-|- Reactivated -|
|- 2 -|-2011-11-16-|- Closed -|
|- 2 -|-2011-11-17-|- Reactivated -|
|- 3 -|-2011-11-15-|- Closed -|
|- 3 -|-2011-11-16-|- Reactivated -|
|- 3 -|-2011-11-17-|- Closed -|
|-ProjectID-|-UpdateDate-|- Status -|
|- 1 -|-2011-11-16-|- Reactivated -|
|- 2 -|-2011-11-17-|- Reactivated -|
答案 2 :(得分:0)
这是我的解决方案(有sp奖励))
CREATE PROC sp_GetReactivatedProjects
AS
SELECT RA.ProjectID
FROM
(SELECT ProjectID, max(UpdateDate) as RaDate
FROM Project
WHERE Status = 'Reactivated'
GROUP BY ProjectID) RA
LEFT JOIN
(SELECT ProjectID, max(UpdateDate) as ClDate
FROM Project
WHERE Status = 'Closed'
GROUP BY ProjectID) Cl
ON RA.ProjectId = Cl.ProjectID
WHERE raDate > ClDate or ClDate is null
希望它会有所帮助
答案 3 :(得分:0)
救援不存在!
-- generate some data
DROP TABLE tmp.projects;
CREATE TABLE tmp.projects
( projectid INTEGER NOT NULL
, updatedate DATE NOT NULL
, status varchar
, PRIMARY KEY (projectid,updatedate)
);
INSERT INTO tmp.projects VALUES
( 1 , '2011-11-15' , 'Closed' )
, ( 1 , '2011-11-16' , 'Reactivated' )
, ( 1 , '2011-11-17' , 'Opened' )
, ( 2 , '2011-11-15' , 'Reactivated' )
, ( 2 , '2011-11-16' , 'Closed' )
, ( 2 , '2011-11-17' , 'Reactivated' )
, ( 3 , '2011-11-15' , 'Closed' )
, ( 3 , '2011-11-16' , 'Reactivated' )
, ( 3 , '2011-11-17' , 'Closed' )
;
SET search_path='tmp';
SELECT * FROM projects p1;
SELECT * FROM projects p1
WHERE status = 'Reactivated'
AND NOT EXISTS ( SELECT *
FROM projects nx
WHERE nx.projectid = p1.projectid
AND nx.updatedate > p1.updatedate
AND nx.status IN ( 'Closed' , 'Reactivated' )
AND NOT EXISTS (SELECT *
FROM projects zlast
WHERE zlast.projectid = nx.projectid
AND zlast.updatedate > nx.updatedate
)
);
结果:
CREATE TABLE
INSERT 0 9
SET
projectid | updatedate | status
-----------+------------+-------------
1 | 2011-11-15 | Closed
1 | 2011-11-16 | Reactivated
1 | 2011-11-17 | Opened
2 | 2011-11-15 | Reactivated
2 | 2011-11-16 | Closed
2 | 2011-11-17 | Reactivated
3 | 2011-11-15 | Closed
3 | 2011-11-16 | Reactivated
3 | 2011-11-17 | Closed
(9 rows)
projectid | updatedate | status
-----------+------------+-------------
1 | 2011-11-16 | Reactivated
2 | 2011-11-17 | Reactivated
(2 rows)
可能存在递归CTE; - )