【问题标题】:SQL Server discriminates between seemingly equal date strings and throws conversion errorSQL Server 区分看似相等的日期字符串并引发转换错误
【发布时间】:2019-02-18 18:44:36
【问题描述】:

从 .csv 导入 dd.(m)m.yyyy 格式的日期字符串后,我似乎无法将它们转换为日期。

使用CONVERT (date, DATE_COLUMN, 104) 会导致错误:

从字符串转换日期和/或时间时转换失败。

但是,如果我尝试转换从列选择输出 (CONVERT (date, '20.5.2018', 104)) 复制的值,则代码对于列中的每个单个值都可以正常工作。

修剪字符串不起作用。我也试过手动改写源文件中的日期字符串,但结果是一样的。

总结(使用 1 个示例值):

select CONVERT(date, DATE_COLUMN, 104)  
from dbo.table

返回:

从字符串转换日期和/或时间时转换失败。

select DATE_COLUMN 
from dbo.table

返回:2018 年 5 月 20 日

select CONVERT(date,'20.5.2018', 104) 

返回:'2018-5-20'

我希望 SQL Server 以相同的方式处理每个转换。虽然有一种解决方法(将字符串拆分为日期部分并将它们组合成日期),但我不明白为什么转换首先会失败。任何帮助表示赞赏。

【问题讨论】:

  • 每一行都有20.5.2018的值吗?
  • select DATE_COLUMN from dbo.table WHERE TRY_CONVERT(date,DATE_COLUMN, 104) IS NULL 返回什么?
  • @Lamak - 20.5.2018 只是一个示例值。
  • 在您的查询select DATE_COLUMN from dbo.table 的返回值中,DATE_COLUMN 值前面是否真的有一个-(减号)?那将是一个危险信号...
  • 又一个很好的例子说明了为什么你不应该将日期存储为字符串。选择正确的数据类型非常重要。 sqlblog.org/2009/10/12/…

标签: sql sql-server type-conversion date-conversion


【解决方案1】:

使用try_convert() 查找问题值:

select DATE_COLUMN 
from dbo.table
where try_convert(date, DATE_COLUMN, 104) is null and
      DATE_COLUMN is not null;

【讨论】:

    【解决方案2】:

    您的问题不可重现。以下测试:

    CREATE TABLE dt (DATE_COLUMN varchar(10));
    
    INSERT INTO dt VALUES ('20.5.2018');
    
    SELECT CONVERT(date, DATE_COLUMN, 104)  
    FROM dt;
    
    DROP TABLE dt;
    

    返回2018-05-20,不会导致任何错误。

    【讨论】:

    • 我认为示例值不是问题;因此我们无法复制这个问题。 OP 自己说他们在字符串文字上的 CONVERT 返回日期 2018-05-20。
    • @Larnu 是的,这个练习的目的是让 OP 相信他们认为问题存在于他们的每一行数据上是不正确的。并且还认为选择具有表提供值的 CONVERT() 函数与字符串文字值之间存在差异。 Martin 的评论提出了正确的调查方法,但 OP 甚至拒绝尝试。
    • @TabAlleman 我不在工作场所,无法在家连接。我明天一定会尝试 try_convert 想法。但是,转换对 '20.5.2018' 值不起作用,12+ 其他相同格式的值,甚至在源文件中手动写入正确的数据都不起作用,因此我建议问题可能出在某个地方别的。明天将发布 try_convert 结果。
    • 好的,正如您在我的回答中看到的那样,转换确实适用于 '20.5.2018' 值,因此您可能在测试中犯了一些错字或其他错误而没有出现在您的问题中,并阻止您获得正确的结果。
    【解决方案3】:

    问题是由于回车符与字符串一起被导入每一行。平面文件连接的行分隔符设置为 {LF},但是一些源平面文件使用 {CR}{LF} 分隔符,因此 {CR} 字符被导入到列中。

    由于我尝试修剪值但没有成功,我的结论是,“隐形”字符都得到了处理。老实说,我从来没有想过可以将回车导入一列。

    由于我无法更改源文件,而且我不确定如何设置导入的动态分隔符,我通过删除 {CR} 解决了这个问题:

    REPLACE(DATE_COLUMN,char(13),'')
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-07-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多