sql格式化和填充列

时间:2017-04-18 22:22:13

标签: sql sql-server-2012

我试图格式化并填充LSD数字看起来像这样。 100 / 14-34-018-09W4 / 00

有时他们在数据库中看起来像这样4-9-62-3W6M。我需要格式化它,使它看起来像100 / 04-09-62-03W6 / 00。有些可能已经或可能没有格式,如果他们已经在前面有100 /或102,那么忽略该部分。

如果缺少前3个数字,则默认为100或填充为100.将M替换为''如果没有或填充00,则在/替换之后结束。在/和/之间的中间,如果其中一个数字是6,则数字为14-34等。所以它是-06-而不是6。

只是想知道是否有人可以指出我正确的方向或最简单的方法来实现这一目标。感谢

2 个答案:

答案 0 :(得分:0)

说实话,我想我会逐步解决这个问题。在开始之前,将表保存在某处,这样就不会发生任何意外情况。

update t
    set lsd = lsd + '/00'
    where lsd not like '%/__';

update t
    set lsd = '100/' + lsd
    where lsd not like '%/%/__';

然后:

update t
    set lsd = stuff(lsd, 5, 0, '0')
    where lsd like '%/_-%';

依此类推,每个职位。这是使用where建立准确的字符串,一次填充一个位置。这可能需要几分钟,但它可能比在一个大型查询中尝试完成所有操作更简单,更安全。

答案 1 :(得分:0)

检查出来:

DECLARE @dummy TABLE(ID INT IDENTITY,YourString VARCHAR(100));
INSERT INTO @dummy VALUES('4-9-62-3W6M')
                        ,('100/4-9-62-3W6M')
                        ,('4-9-62-3W6M/3')
                        ,('102/4-9-62-3W6M')
                        ,('5/4-9-62-3W6/5');

WITH Splitted AS
(
    SELECT 
           ID
          ,d.YourString 
          ,CAST('<x>' + REPLACE(REPLACE(d.YourString,'/','-'),'-','</x><x>') + '</x>' AS XML) AS TheXML
          ,CASE WHEN CHARINDEX('/',d.YourString)>0 AND CHARINDEX('/',d.YourString)<CHARINDEX('-',d.YourString) 
                THEN 1 ELSE 0 
           END AS HasPrefix
    FROM @dummy AS d
) 
,Parted AS
(
    SELECT *
          ,CASE WHEN HasPrefix=1 THEN TheXML.value('(/x)[1]','nvarchar(max)') 
                                 ELSE '100' END AS Prefix
          ,TheXML.value('(/x)[1+sql:column("HasPrefix")][1]','nvarchar(max)') AS Part1
          ,TheXML.value('(/x)[2+sql:column("HasPrefix")][1]','nvarchar(max)') AS Part2
          ,TheXML.value('(/x)[3+sql:column("HasPrefix")][1]','nvarchar(max)') AS Part3
          ,TheXML.value('(/x)[4+sql:column("HasPrefix")][1]','nvarchar(max)') AS Part4
          ,TheXML.value('(/x)[5+sql:column("HasPrefix")][1]','nvarchar(max)') AS PostFix
    FROM Splitted
)
SELECT REPLACE(STR(Prefix,3),' ','0') + '/'
      +REPLACE(STR(Part1,2),' ','0') + '-'
      +REPLACE(STR(Part2,2),' ','0') + '-'
      +REPLACE(STR(Part3,2),' ','0') + '-'
      +CASE WHEN RIGHT(Part4,1)='M' THEN LEFT(Part4,LEN(Part4)-1) ELSE Part4 END + '/'
      +ISNULL(REPLACE(STR(PostFix,2),' ','0'),'00')
FROM Parted

结果

100/04-09-62-3W6/00
100/04-09-62-3W6/00
100/04-09-62-3W6/03
102/04-09-62-3W6/00
005/04-09-62-3W6/05

发生了什么事?

将一些测试数据插入模拟表后,我使用一个CTE将字符串拆分为连字符。在此之前,斜杠替换为连字符,因此我们分别得到每个部分。

标志HasPrefix告诉我们,给定的代码是否有前缀(如100/)。我们在第二个CTE中使用此标志,我们从拆分的字符串中检索部分作为add-parameter来查找实际位置。

最终SELECT将使用STR()REPLACE作为填充,并将部分连接到一个字符串。

如果您愿意,可以在最后设置SELECT * FROM以查看所有中间步骤。