代码之家  ›  专栏  ›  技术社区  ›  Osti

TSQL获取以范围或逗号分隔的数字

  •  0
  • Osti  · 技术社区  · 6 年前

    现在我把它和逗号分隔的字符串结合起来。 我现在举个例子:1-001,1-002,1-003

    但是如果数字是1-001,1-002,1-003,1-004,1-007,我想得到这个包成员的范围是有序的,这个范围(或单个包)用逗号分隔。

    Packagings: 1-001, 1-002, 1-003, 1-004, 1-007, 1-008, 2-001
    Expected: 1-001 to 1-004, 1-007 to 1-008, 2-001
    

    我现在的方法是这样的:

    SELECT
        o.OrderNumber 
        , op.PositionNumber
        , STUFF((
            SELECT ',' + ifp.Packnumber
            FROM FilledPackage ifp
            INNER JOIN PositionInFIlledPackage pifp
            ON ifp.FilledPackageId = pifp.FilledPackageId
            WHERE 
                ifp.OrderNumber = o.OrderNumber
                AND pifp.PositionNumber = op.PositionNumber
            ORDER BY ifp.Code, ifp.PackOfTypeCounter
            FOR XML PATH(''),TYPE).value('(./text())[1]','VARCHAR(MAX)')
          ,1,1,'') AS Packagings
    FROM MyOrder o
    INNER JOIN MyPosition op
    ON o.OrderId = op.OrderId
    GROUP BY 
        o.OrderNumber 
        , op.PositionNumber
    
    • ifp.Code是包装类型(如1/1-00x)
    • packoftypeconter是某个类型(如x-001中的1)的当前Packagenumber
    • PackNumber是一个类似于1-002的字符串(1=>包类型,2=>PackageNumber) 示例:PackNumber=ifp.Code+“-”+ifp.packoftypeconter

    最后我想要这样的东西:

    Position 1: Pack: 4-001 to 4-008
    Position 2: Pack: 1-001 to 1-004, 2-001 to 2-002, 4-009
    Position 3: Pack: 4-010
    Position 3: Pack: 1-005 to 1-007, 4-011
    

    从这样的角度来看:

    • 位置编号
    • 包代码(int)=>包类型=>1
    • PackOfTypeCounter(整数)=>001
    • 全包成员(1-001)

    谢谢你的帮助

    1 回复  |  直到 6 年前
        1
  •  2
  •   Alan Burstein    6 年前

    你问得太多了,让我们先关注一下这个要求:

    Packagings: 1-001, 1-002, 1-003, 1-004, 1-007, 1-008, 2-001
    Expected: 1-001 to 1-004, 1-007 to 1-008, 2-001
    

    DelimitedSplit8K

    DECLARE @packagings VARCHAR(1000) = '1-001, 1-002, 1-003, 1-004, 1-007, 1-008, 2-001';
    
    SELECT STUFF(
    (
      SELECT 
        ', '+
        CASE 
          WHEN MIN(g.txt) = MAX(g.txt) 
          THEN CAST(g.txtGroup AS VARCHAR(100))+'-'+CAST(MIN(g.txt) AS VARCHAR(100)) 
          ELSE CAST(g.txtGroup AS VARCHAR(100))+'-'+CAST(MIN(g.txt) AS VARCHAR(100))+' to '+
               CAST(g.txtGroup AS VARCHAR(100))+'-'+CAST(MAX(g.txt) AS VARCHAR(100))
        END
      FROM
      (
        SELECT txtGroup = t1.txt, t2.txt, grouper = t2.txt - split.ItemNumber
        FROM dbo.DelimitedSplit8K(REPLACE(@packagings,' ',''),',') AS split
        CROSS APPLY (VALUES(CHARINDEX('-', split.item)))           AS mid(pos)
        CROSS APPLY (VALUES(SUBSTRING(split.item,1,mid.pos-1)))    AS t1(txt)
        CROSS APPLY (VALUES(SUBSTRING(split.item,mid.pos+1,8000))) AS t2(txt)
      ) g
      GROUP BY g.txtGroup, g.grouper
      ORDER BY g.txtGroup
      FOR XML PATH('')
    ),1,2,'');
    

    返回:

    1-001 to 1-004, 1-007 to 1-008, 2-001