2010-08-23 49 views
8

是否有一種將掩碼應用於SQL Server查詢中的字符串的簡便方法?在SQL Server查詢/視圖中應用掩碼來格式化字符串

我有兩個表,一個存儲爲varchar,沒有文字0155567890和電話類型,其具有該電話號碼類型口罩電話號碼:(##) #### ####

什麼是返回一個字符串的最佳方式(對於合併文檔),以便查詢返回完全格式化的電話號碼:

(01) 5556 7890 
+0

我的回答對你有幫助嗎? – 2010-08-24 07:56:55

回答

7

我需要這也和感謝Sjuul的僞代碼,我能夠創建一個函數來做到這一點。

CREATE FUNCTION [dbo].[fx_FormatUsingMask] 
(
    -- Add the parameters for the function here 
    @input nvarchar(1000), 
    @mask nvarchar(1000) 
) 
RETURNS nvarchar(1000) 
AS 
BEGIN 
    -- Declare the return variable here 
    DECLARE @result nvarchar(1000) = '' 
    DECLARE @inputPos int = 1 
    DECLARE @maskPos int = 1 
    DECLARE @maskSign char(1) = '' 

    WHILE @maskPos <= Len(@mask) 
    BEGIN 
     set @maskSign = substring(@mask, @maskPos, 1) 

     IF @maskSign = '#' 
     BEGIN 
      set @result = @result + substring(@input, @inputPos, 1) 
      set @inputPos += 1 
      set @maskPos += 1 
     END 
     ELSE 
     BEGIN 
      set @result = @result + @maskSign 
      set @maskPos += 1 
     END 
    END 
    -- Return the result of the function 
    RETURN @result 

END 
2

這正是我腦子裏想到的。我不知道這是否是最好的解決方案,但我認爲它應該是可行的。

建立一個名爲applyMask(公積金)

僞功能:

WHILE currentPosition < Length(PhoneNr) AND safetyCounter < Length(Mask) 
    IF currentSign = "#" 
     result += Mid(PhoneNr, currentPosition, 1) 
     currentPosition++ 
    ELSE 
     result += currentSign 
     safetyCounter++ 
    END 
END 
Return result 
2

以防萬一某人會需要表值函數。

方法1

create function ftMaskPhone 
(
    @phone varchar(30), 
    @mask varchar(50) 
) 
returns table as 
return 
    with ci(n, c, nn) as (
     select 
      1, 
      case 
       when substring(@mask, 1, 1) = '#' then substring(@phone, 1, 1) 
       else substring(@mask, 1, 1) 
      end, 
      case when substring(@mask, 1, 1) = '#' then 1 else 0 end 
     union all 
     select 
      n + 1, 
      case 
       when substring(@mask, n + 1, 1) = '#' then substring(@phone, nn + 1, 1) 
       else substring(@mask, n + 1, 1) 
      end, 
      case when substring(@mask, n + 1, 1) = '#' then nn + 1 else nn end 
     from ci where n < len(@mask)) 
    select (select c + '' from ci for xml path(''), type).value('text()[1]', 'varchar(50)') PhoneMasked 
GO 

然後應用它作爲

declare @mask varchar(50) 
set @mask = '(##) #### ####' 

select pm.PhoneMasked 
from Phones p 
    outer apply ftMaskPhone(p.PhoneNum, @mask) pm 

方法2

讓我們離開abowe一個歷史。下面一個是更高性能的。

create function ftMaskPhone 
(
    @phone varchar(30), 
    @mask varchar(50) 
) 
returns table as 
return 
    with v1(N) as (
     select 1 union all select 1 union all select 1 union all select 1 union all select 1 
     union all 
     select 1 union all select 1 union all select 1 union all select 1 union all select 1 
    ), 
    v2(N) as (select 1 from v1 a, v1 b), 
    v3(N) as (select top (isnull(len(@mask), 0)) row_number() over (order by @@spid) from v2), 
    v4(N, C) as (
     select N, isnull(substring(@phone, case when c.m = 1 then row_number() over (partition by c.m order by N) end, 1), substring(@mask, v3.N, 1)) 
     from v3 
      cross apply (select case when substring(@mask, v3.N, 1) = '#' then 1 end m) c 
    ) 
    select Value = (
     select c + '' 
     from v4 
     order by N 
     for xml path(''), type 
    ).value('text()[1]', 'varchar(50)') 
go 
0

如果您需要在「面具」,而隱藏與另一個真正的價值,然後在「揭露」的字符串,你可以試試這個功能,或者延長其對這一問題。 :)

https://stackoverflow.com/a/22023329/2175524