sql-server - 是否可以简化此 patindex 代码?
问题描述
我一直在寻找一种方法来简化下面的 patindex 代码,但还没有成功。有没有人可以告诉我这是否可能在 SQL Server 中。
patindex('%'+'('+'[0-9][0-9]'+'/'+'[0-9][0-9]'+'/'+'[0-9][0-9][0-9][0-9]'+' - '+'[0-9][0-9]'+'/'+'[0-9][0-9]'+'/'+'[0-9][0-9][0-9][0-9]'+')'+'%', ii.description)
该字符串始终包含日期部分,例如 (17/09/2015 - 16/09/2016),我想从该字符串中获取两个日期。这个想法是,我用两个日期寻找这个文本块的起点,然后用一个子字符串函数(和一些数学)计算开始日期和结束日期的位置和内容。
如果有更简单或更好的方法来做到这一点,我愿意接受建议。非常感谢。
解决方案
有几种方法可以清理你拥有的东西,也有很多方法可以解决这个问题。
DECLARE @text VARCHAR(100) = '(17/09/2015 - 16/09/2016)';
--==== Solution #1: Basic position matching
SELECT
Date1 = SUBSTRING(@text,2,10),
Date2 = SUBSTRING(@text,15,10);
--==== Solution #2: Cleanup using APPLY
SELECT TheDate = PATINDEX('%('+fmt.Phone+' - '+fmt.Phone+')%', @text)
FROM (VALUES('[0-9][0-9]/[0-9][0-9]/[0-9][0-9][0-9][0-9]')) AS fmt(Phone);
--==== Solution #3: Use 2nd APPLY call for the Second Date; MUCH CLEANER!
SELECT
Date1 = SUBSTRING(@text,p1.Pos,10),
Date2 = SUBSTRING(@text,p1.Pos+12,10)
FROM (VALUES('%[0-9][0-9]/[0-9][0-9]/[0-9][0-9][0-9][0-9]%')) AS fmt(Phone)
CROSS APPLY (VALUES(PATINDEX(fmt.Phone,@text))) AS p1(Pos)
CROSS APPLY (VALUES(SUBSTRING(@text,p1.Pos+12,10))) AS st2(Txt)
这三个查询返回:
Date1 Date2
---------- ----------
17/09/2015 16/09/2016
TheDate (location of first date)
-----------
1
Date1 Date2
---------- ----------
17/09/2015 16/09/201
使用NGrams8k时,这样的东西非常简单快捷。
--==== Solution #3 Ngrams8k
SELECT TheDate = f.Dt
FROM dbo.ngrams8k(@text,10) AS ng
CROSS APPLY (VALUES(TRY_CONVERT(DATE,ng.token,103))) AS f(Dt)
WHERE CHARINDEX('/',ng.token) = 3
AND f.Dt IS NOT NULL;
--==== Solution #4 Ngrams8k with Pivot
SELECT
Date1 = MAX(CASE f.RN WHEN 1 THEN f.DT END),
Date2 = MAX(CASE f.RN WHEN 2 THEN f.DT END)
FROM
(
SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)), f.Dt
FROM dbo.ngrams8k(@text,10) AS ng
CROSS APPLY (VALUES(TRY_CONVERT(DATE,ng.token,103))) AS f(Dt)
WHERE CHARINDEX('/',ng.token) = 3
AND f.Dt IS NOT NULL
) AS f(RN,DT);
这些返回:
TheDate
----------
2015-09-17
2016-09-16
Date1 Date2
---------- ----------
2015-09-17 2016-09-16
第一个解决方案将日期作为行返回,第二个解决方案是旋转的。无论您需要什么。
推荐阅读
- firebase - 如何在 Flutter 上获取 Firebase Firestore 异常代码?
- php - Wordpress 查询关系 AND 与 meta_query 和 tax_query
- java - 是否可以在 pycharm ide 中使用 java 模块编译和执行项目?
- python - 使用 for 循环查找偶数或奇数的代码问题
- flutter - Flutter类报错,尝试添加初始化表达式,或者在这个构造函数中添加字段初始化,或者标记一下
- python - AttributeError:“spacy.tokens.span.Span”对象没有属性“字符串”
- python - 根据定义的列数自动创建熊猫列
- flask - 连接到 5000 端口后如何输入命令?
- java - 无法连接到数据库 java jsp、servlet
- kubernetes - Kubernetes 中的 RBAC