用于标记各行的T-SQL

时间:2017-06-30 19:20:26

标签: sql tsql cursor

我正在寻找一些T-SQL代码,它会添加一个名为tag的列,它会用相同的数字标记每一行,直到“team”,“id”,“id”,“id”,“ kmvid“,”name“,”cid“和”pid“。如果有更改,请使用该行的下一个编号序列。请参阅下面的预期结果作为图像。

enter image description here

2 个答案:

答案 0 :(得分:0)

您可以使用累计金额和lag()

执行此操作
select t.*,
       sum(case when prev_team = team and
                     id = id and
                     kmvid = kmvid and
                     name = name and
                     prev_id = id and
                     prev_cid = pid and
                     prev_oid = cid
                 then 1 else 0
            end) over (order by date) as Tag
from (select t.*,
             lag(team) over (order by date) as prev_team,
             lag(id) over (order by date) as prev_id,
             lag(kmvid) over (order by date) as prev_kmvid,
             lag(name) over (order by date) as prev_name,
             lag(cid) over (order by date) as prev_cid,
             lag(pid) over (order by date) as prev_pid
      from t
     ) t;

您不应该使用游标来处理使用基于集合的操作做得更好的事情。

答案 1 :(得分:0)

以下内容将根据您拍摄的数据...

为您提供所需的结果
IF OBJECT_ID('tempdb..#TestData', 'U') IS NOT NULL 
DROP TABLE #TestData;

CREATE TABLE #TestData (
    CountryId CHAR(2) NOT NULL,
    [Date] DATETIME NOT NULL
    );
INSERT #TestData (CountryId, Date)
SELECT '99', '2004-04-30' UNION ALL 
SELECT '99', '2004-07-31' UNION ALL 
SELECT '99', '2004-10-31' UNION ALL 
SELECT '99', '2005-01-31' UNION ALL 
SELECT '99', '2005-04-30' UNION ALL 
SELECT '99', '2005-07-31' UNION ALL 
SELECT '99', '2005-10-31' UNION ALL
SELECT '99', '2006-01-31' UNION ALL 
SELECT '99', '2006-04-30' UNION ALL 
SELECT '99', '2006-07-31' UNION ALL 
SELECT '99', '2006-10-31' UNION ALL 
SELECT '99', '2007-01-31' UNION ALL 
SELECT 'HK', '2007-04-30' UNION ALL 
SELECT 'CA', '2007-07-31' UNION ALL 
SELECT 'HK', '2007-10-31';

--  SELECT * FROM #TestData td;

--=======================================

WITH 
    cte_TagGroup AS (
        SELECT 
            td.CountryId, 
            td.[Date],
            TagGroup = ROW_NUMBER() OVER (ORDER BY td.Date)
                - ROW_NUMBER() OVER (PARTITION BY td.CountryId ORDER BY td.Date)
                - CASE WHEN td.CountryId = LAG(td.CountryId, 1, td.CountryId) OVER (ORDER BY td.CountryId, td.Date) THEN 0 ELSE 1 END
        FROM
            #TestData td
        )
SELECT 
    tg.CountryId, 
    tg.Date, 
    Tag = DENSE_RANK() OVER (ORDER BY tg.TagGroup)
FROM
    cte_TagGroup tg;

...那就是说,我怀疑前三列数据的值并不完全相同,因此您可能需要在“PARTITION BY”子句中添加列以使其适合您的实际数据。

HTH,

杰森