을 감안할 때이
SELECT * FROM T;
+------+------+--------+
| ID | DATE | STATUS |
+------+------+--------+
| 1 | 106 | A |
| 1 | 107 | A |
| 1 | 112 | A |
| 1 | 130 | B |
| 1 | 201 | A |
| 2 | 102 | C |
| 2 | 107 | C |
+------+------+--------+
그것은이
SELECT T.ID,T.DATE,T.STATUS,
IF(STATUS <> @PREVS,@RN:[email protected]+1,@RN:[email protected]) RNBLOCK ,
IF(STATUS = @PREVS,@RN2:[email protected]+1,@RN2:=1) RNSEQ ,
@PREVS:=STATUS PSTATUS
FROM (SELECT @RN:=1) RNBLOCK, (SELECT @RN2:=0) RNSEQ,(SELECT @PREVS:=NULL) P, T
우리가 고립 그래서 이제 블록이
+------+------+--------+---------+-------+---------+
| ID | DATE | STATUS | RNBLOCK | RNSEQ | PSTATUS |
+------+------+--------+---------+-------+---------+
| 1 | 106 | A | 1 | 1 | A |
| 1 | 107 | A | 1 | 2 | A |
| 1 | 112 | A | 1 | 3 | A |
| 1 | 130 | B | 2 | 1 | B |
| 1 | 201 | A | 3 | 1 | A |
| 2 | 102 | C | 4 | 1 | C |
| 2 | 107 | C | 4 | 2 | C |
+------+------+--------+---------+-------+---------+
을 줄 안다는 사용하여 블록 및 SEQNO을 할당하는 것은 매우 간단합니다 min seq no (1)과 max seqno를 테이블로 밀어 넣을 수 있습니다.
drop table t1;
CREATE TABLE `t1` (
`ID` INT(11) NULL DEFAULT NULL,
`DATE` INT(11) NULL DEFAULT NULL,
`STATUS` VARCHAR(1) NULL DEFAULT NULL,
`rnblock` int null default null,
`rnseq` int null default null,
`pstatus` VARCHAR(1) NULL DEFAULT NULL
)
COLLATE='latin1_swedish_ci'
ENGINE=InnoDB
;
간단한 분 최대를 만들이
+------+------+------+--------+
| ID | DATE | DATE | STATUS |
+------+------+------+--------+
| 1 | 106 | 112 | A |
| 1 | 130 | 130 | B |
| 1 | 201 | 201 | A |
| 2 | 102 | 107 | C |
+------+------+------+--------+
단점은 당신이 그것을 작동하도록 테이블을 작성해야한다는 것입니다 얻을
SELECT T2.ID,T2.DATE,T3.DATE,T2.STATUS FROM
(
SELECT T1.RNBLOCK,MAX(T1.RNSEQ) MAXSEQ
FROM T1
GROUP BY RNBLOCK
) S
JOIN T1 T2 ON T2.RNBLOCK = S.RNBLOCK AND T2.RNSEQ = 1
JOIN T1 T3 ON T3.RNBLOCK = S.RNBLOCK AND T3.RNSEQ = S.MAXSEQ
가입 할 수 있습니다.
또는 당신은 중간 테이블
select u.id,u.date,v.date,u.status from
(
select s.rnblock,s.status,min(s.rnseq) minseq,max(s.rnseq) maxseq
from
(
SELECT T.ID,T.DATE,T.STATUS,
IF(STATUS <> @PREVS,@RN:[email protected]+1,@RN:[email protected]) RNBLOCK ,
IF(STATUS = @PREVS,@RN2:[email protected]+1,@RN2:=1) RNSEQ ,
@PREVS:=STATUS PSTATUS
FROM (SELECT @RN:=1) RNBLOCK, (SELECT @RN2:=0) RNSEQ,(SELECT @PREVS:=NULL) P, T
) s
group by s.rnblock,s.status
) T
join
(SELECT T.ID,T.DATE,T.STATUS,
IF(STATUS <> @PREVS2,@RN3:[email protected]+1,@RN3:[email protected]) RNBLOCK ,
IF(STATUS = @PREVS2,@RN4:[email protected]+1,@RN4:=1) RNSEQ ,
@PREVS2:=STATUS PSTATUS
FROM (SELECT @RN3:=1) RNBLOCK, (SELECT @RN4:=0) RNSEQ,(SELECT @PREVS2:=NULL) P, T
) u on u.rnblock = t.rnblock and u.rnseq = minseq
join
(SELECT T.ID,T.DATE,T.STATUS,
IF(STATUS <> @PREVS3,@RN5:[email protected]+1,@RN5:[email protected]) RNBLOCK ,
IF(STATUS = @PREVS3,@RN6:[email protected]+1,@RN6:=1) RNSEQ ,
@PREVS3:=STATUS PSTATUS
FROM (SELECT @RN5:=1) RNBLOCK, (SELECT @RN6:=0) RNSEQ,(SELECT @PREVS3:=NULL) P, T
) v on v.rnblock = t.rnblock and v.rnseq = maxseq
I에 대한이 조금에 대한 생각을 사용하지 않는이 오히려 꼴 사나운 코드를 사용할 수 있습니다. 그리고 주어진 종소리와 호각이 MySQL에서 사용 가능하다는 것을 알지 못한다. (T/SQL은 현재 적용 가능한 앞뒤 지연 기능을 가지고있다.) 나는 정직한 순수 SQL 솔루션을 생각할 수 없었다. 그러나, 그리고 interative 접근 방식은 간단합니다. 해당 데이터를 사용자가 가지고있는 방식대로 순서대로 정렬하고 반복하며 ID 또는 상태가 이전 행보다 언제 변경되었는지를 감지합니다. 시작 또는 종료 시간 또는 상태 또는 ID 변경 여부입니다. 각 전환에 대해 새 테이블에 행을 삽입하십시오. –
저장 프로 시저를 사용하여 트릭을 사용할 수 있습니다. –