从文本中获取日期时间
Get DateTime from text
如何从字符串中分离并仅显示日期时间?
我有一列包含此数据:
Comments
-----------------------------------------
Daniel reached the school by 9:25:00 alone
Breakfast was served by 10:17:27 in the morning
Reached back home late evening by 7:00:48
我用这个查询来分离时间:
(CONVERT(varchar(max), Comments, 108)) [Comments],
它返回相同的行。字符串未被过滤
当我尝试使用此语句时:
(CONVERT(TIME, Comments, 108)) [Comments],
我遇到了这个错误
Conversion failed when converting date and/or time from character string.
我怎样才能克服时间并获得低于预期的结果?
Comments
----------------------------------------
9:25:00
10:17:27
7:00:48
ltrim(substring(comments, charindex(comments, ':') - 2, 8))
显然,这假设总有一个冒号,并且第一个冒号在时间元素内。它还假定所有时间都有前导 space 并且长度为 7-8 个字符。根据你打算用这个做什么,ltrim()
可能是不必要的。
这只是字符串解析。我意识到这实际上并没有转换为时间值,因为不清楚 OP 在输出中要求它。
使用 patindex 您可以找到时间模式。
select
try_cast(substring(Comments, patindex('%[ 0-9][0-9]:[0-9][0-9]:[0-9][0-9]%', Comments), 8) as time(0)) CommentTime
from your_table
CommentTime
09:25:00
10:17:27
07:00:48
您可以使用 STRING_SPLIT
和 TRY_CONVERT
。
SELECT Tbl.Comments, T.value
FROM Tbl CROSS APPLY STRING_SPLIT(Tbl.Comments,' ') As T
WHERE TRY_CONVERT(TIME, value) IS NOT NULL
对于不支持STRING_SPLIT
的版本,可以使用XML
实现相同的逻辑,因为已经有使用PATINDEX
的解决方案。
WITH cte AS (
SELECT Comments, CONVERT(XML, CONCAT('<n>',REPLACE(Comments,' ','</n><n>'),'</n>')) AS x
FROM Tbl)
SELECT cte.Comments, v.value('.','varchar(MAX)')
FROM cte CROSS APPLY x.nodes('/n') AS t(v)
WHERE TRY_CONVERT(TIME, v.value('.','varchar(MAX)')) IS NOT NULL
如何从字符串中分离并仅显示日期时间?
我有一列包含此数据:
Comments
-----------------------------------------
Daniel reached the school by 9:25:00 alone
Breakfast was served by 10:17:27 in the morning
Reached back home late evening by 7:00:48
我用这个查询来分离时间:
(CONVERT(varchar(max), Comments, 108)) [Comments],
它返回相同的行。字符串未被过滤
当我尝试使用此语句时:
(CONVERT(TIME, Comments, 108)) [Comments],
我遇到了这个错误
Conversion failed when converting date and/or time from character string.
我怎样才能克服时间并获得低于预期的结果?
Comments
----------------------------------------
9:25:00
10:17:27
7:00:48
ltrim(substring(comments, charindex(comments, ':') - 2, 8))
显然,这假设总有一个冒号,并且第一个冒号在时间元素内。它还假定所有时间都有前导 space 并且长度为 7-8 个字符。根据你打算用这个做什么,ltrim()
可能是不必要的。
这只是字符串解析。我意识到这实际上并没有转换为时间值,因为不清楚 OP 在输出中要求它。
使用 patindex 您可以找到时间模式。
select try_cast(substring(Comments, patindex('%[ 0-9][0-9]:[0-9][0-9]:[0-9][0-9]%', Comments), 8) as time(0)) CommentTime from your_table
CommentTime 09:25:00 10:17:27 07:00:48
您可以使用 STRING_SPLIT
和 TRY_CONVERT
。
SELECT Tbl.Comments, T.value
FROM Tbl CROSS APPLY STRING_SPLIT(Tbl.Comments,' ') As T
WHERE TRY_CONVERT(TIME, value) IS NOT NULL
对于不支持STRING_SPLIT
的版本,可以使用XML
实现相同的逻辑,因为已经有使用PATINDEX
的解决方案。
WITH cte AS (
SELECT Comments, CONVERT(XML, CONCAT('<n>',REPLACE(Comments,' ','</n><n>'),'</n>')) AS x
FROM Tbl)
SELECT cte.Comments, v.value('.','varchar(MAX)')
FROM cte CROSS APPLY x.nodes('/n') AS t(v)
WHERE TRY_CONVERT(TIME, v.value('.','varchar(MAX)')) IS NOT NULL