SQL Server拆分字符串并访问其不同部分
我需要更新存储在列中的url 我的列具有如下值:SQL Server拆分字符串并访问其不同部分,sql,sql-server,Sql,Sql Server,我需要更新存储在列中的url 我的列具有如下值: https://www.site.sharepoint.com/sites/test/AB-19-CALL urlCompte.Split('-')[2] + urlCompte.Split('-')[0] + urlCompte.Split('-')[1] 我想将此URL更新为: https://www.site.sharepoint.com/sites/test/CALL-AB-19 为了得到最后一部分,即AB-19-CALL,我使用
https://www.site.sharepoint.com/sites/test/AB-19-CALL
urlCompte.Split('-')[2] + urlCompte.Split('-')[0] + urlCompte.Split('-')[1]
我想将此URL更新为:
https://www.site.sharepoint.com/sites/test/CALL-AB-19
为了得到最后一部分,即AB-19-CALL
,我使用了下面的查询
SELECT
SUBSTRING(urlcompte, LEN(urlcompte) - CHARINDEX('/', REVERSE(urlcompte)) + 2, LEN(urlcompte)),
UrlCompte
FROM
tblAccount
现在要拆分和反转AB-19-call
,我需要再次使用上面的整个查询,然后使用-
选择子字符串
有没有更简单的方法
在C#中,我们可以这样做:
https://www.site.sharepoint.com/sites/test/AB-19-CALL
urlCompte.Split('-')[2] + urlCompte.Split('-')[0] + urlCompte.Split('-')[1]
SQL Server中是否有方法拆分列并访问其中的不同部分 这将有助于拆分字符串部分-
DECLARE @txt NVARCHAR(500)= 'https://www.site.sharepoint.com/sites/test/AB-19-CALL';
SELECT value
FROM STRING_SPLIT(REVERSE(SUBSTRING(REVERSE(@txt), 1, CHARINDEX('/', REVERSE(@txt))-1)), '-');(substring(reverse(@txt),1,charindex('/',reverse(@txt))-1)),'-')
如果您有幸使用SQL Server 2017,您可以使用 下面是更改url最后一部分顺序的脚本
declare @url varchar(100) = 'CALL-AB-19'
select
string_agg(value,'-') within group (order by rn desc)
from (
select
value, row_number() over (order by @url) as rn
from STRING_SPLIT( @url , '-' )
) t
如果希望使用一条SELECT语句将此解决方案作为基于集合的解决方案应用于表行,则可以执行以下SQL
select
id, string_agg(value,'-') within group (order by rn desc)
from (
select
id, value, row_number() over (partition by id order by url) as rn
from urlList
cross apply STRING_SPLIT( url , '-' )
) t
group by id
我假设,在您的表URL列表中,您有一个PK字段id
如果您没有将SQL Server 2016用于拆分函数,而将SQL Server 2017用于字符串聚合函数,则可以在web上搜索示例。使用FOR XML Path连接字符串部分,您可以在CTE表达式的帮助下构建一个解决方案,如下所示
;with cte as (
select
urlList.id,
urlList.url,
s.id sid,
s.val
from urlList
cross apply dbo.split(url,'-' ) s
)
SELECT
distinct
id,
STUFF(
(
SELECT
'-' + u.val
FROM cte as u
where u.id = cte.id
Order By sid desc
FOR XML PATH('')
), 1, 1, ''
) As newurl
FROM cte
请注意,引用的split函数返回一个名为numeric的id字段,该字段显示被拆分部分的顺序。因此,在连接时,我在同一字段上使用了一个“order by”子句,这次是降序的如果有人正在使用SQL server 2012或更早版本,则可以通过以下方式实现:
DECLARE @URL VARCHAR(100) = 'https://www.site.sharepoint.com/sites/test/AB-19-CALL'
SELECT TOP 1 dbo.[Reversedata](DATA, '-')
FROM (SELECT * FROM dbo.Splitter(@URL, '/') as t) as tt order by Id desc
在上述代码中,我使用了两个函数:
1) 拆分器:拆分字符串()
2) Reversedata:要反转数据()
拆分器:
CREATE FUNCTION [dbo].[Splitter]
(
@String NVARCHAR(4000),
@Delimiter NCHAR(1)
)
RETURNS TABLE
AS
RETURN
(
WITH Split(stpos,endpos)
AS(
SELECT 0 AS stpos, CHARINDEX(@Delimiter,@String) AS endpos
UNION ALL
SELECT endpos+1, CHARINDEX(@Delimiter,@String,endpos+1)
FROM Split
WHERE endpos > 0
)
SELECT 'Id' = ROW_NUMBER() OVER (ORDER BY (SELECT 1)),
'Data' = SUBSTRING(@String,stpos,COALESCE(NULLIF(endpos,0),LEN(@String)+1)-stpos)
FROM Split
)
GO
CREATE FUNCTION [dbo].[udf_ReverseSequenceOrder] (
@Input nvarchar(200)
,@Delimiter nvarchar(5)
)
RETURNS nvarchar(200)
AS
BEGIN
DECLARE @Output nvarchar(200)
WHILE LEN(@Input) > 0
BEGIN
IF CHARINDEX(@Delimiter, @Input) > 0
BEGIN
SET @Output = SUBSTRING(@Input,0,CHARINDEX(@Delimiter, @Input)) + @Delimiter + ISNULL(@Output,'')
SET @Input = SUBSTRING(@Input,CHARINDEX(@Delimiter, @Input)+1,LEN(@Input))
END
ELSE
BEGIN
SET @Output = @Input + @Delimiter + ISNULL(@Output,'')
SET @Input = ''
END
END
RETURN SUBSTRING(@Output,0,LEN(@Output))
END
反向:
CREATE FUNCTION [dbo].[Splitter]
(
@String NVARCHAR(4000),
@Delimiter NCHAR(1)
)
RETURNS TABLE
AS
RETURN
(
WITH Split(stpos,endpos)
AS(
SELECT 0 AS stpos, CHARINDEX(@Delimiter,@String) AS endpos
UNION ALL
SELECT endpos+1, CHARINDEX(@Delimiter,@String,endpos+1)
FROM Split
WHERE endpos > 0
)
SELECT 'Id' = ROW_NUMBER() OVER (ORDER BY (SELECT 1)),
'Data' = SUBSTRING(@String,stpos,COALESCE(NULLIF(endpos,0),LEN(@String)+1)-stpos)
FROM Split
)
GO
CREATE FUNCTION [dbo].[udf_ReverseSequenceOrder] (
@Input nvarchar(200)
,@Delimiter nvarchar(5)
)
RETURNS nvarchar(200)
AS
BEGIN
DECLARE @Output nvarchar(200)
WHILE LEN(@Input) > 0
BEGIN
IF CHARINDEX(@Delimiter, @Input) > 0
BEGIN
SET @Output = SUBSTRING(@Input,0,CHARINDEX(@Delimiter, @Input)) + @Delimiter + ISNULL(@Output,'')
SET @Input = SUBSTRING(@Input,CHARINDEX(@Delimiter, @Input)+1,LEN(@Input))
END
ELSE
BEGIN
SET @Output = @Input + @Delimiter + ISNULL(@Output,'')
SET @Input = ''
END
END
RETURN SUBSTRING(@Output,0,LEN(@Output))
END
这就是基于xml的解决方案。适用于SQL Server 2008及以上版本
DECLARE @url VARCHAR(100) = 'AB-19-CALL'
SELECT MyUrl FROM
(
SELECT CAST('<Url><Part>' + REPLACE(@url,'-','</Part><Part>') + '</Part></Url>' AS XML) AS my_Xml
) t1
CROSS APPLY
(
SELECT
my_Data.D.value('Part[3]','varchar(50)') + '-' +
my_Data.D.value('Part[1]','varchar(50)') + '-' +
my_Data.D.value('Part[2]','varchar(50)') AS MyUrl
FROM t1.my_Xml.nodes('/Url') as my_Data(D)
) t2
如果您知道最后一个零件中永远不会包含“.”(例如
AB-1.9-CALL
),则可以将-
替换为
,并使用该功能。如果您运行的是SQL Server 2016及更高版本,则会更轻松。