从 varchar 转换为 datetime 时,SQL 服务器实例使用的默认日期样式是什么?

What is the default date style used by an instance of SQL Server when converting from varchar to datetime?

我在两个不同的服务器上 运行 这个 SQL 查询:

declare @test as datetime='2020-05-06 00:00:00'
select Convert (nvarchar,@test) 

两个服务器上的结果不同:

  1. 2020 年 5 月 6 日12:00AM
  2. 2020 年 6 月 5 日12:00AM

我知道这背后的原因,当 SQL 服务器读取我传递给 2020-05-06 00:00:00 的字符串并在声明语句中将其转换为 DateTime 时,它使用的是默认日期风格。

我是否可以配置此默认样式,或者换句话说,在将 varchar 转换为 datetime 时,SQL 服务器中如何选择默认日期样式?是来自 windows 区域设置还是 SQL 服务器内部的一些其他配置?

它使用基于语言的样式。基本上,对于上面的日期,如果您是美国人,那么日期将读作 yyyy-MM-dd hh:mm:ss,但是,如果使用多种语言,那么它会(愚蠢地)读作 yyyy-dd-MM hh:mm:ss.

如果您对日期使用字符串(如此处的文字),则应使用明确的格式。在SQL服务器中,无论数据类型和语言如何,都是yyyy-MM-ddThh:mm:ss.nnnnnnnyyyyMMdd

如果您要转换为 (n)varchar,请始终使用 style code(以及 varchar 的长度)以获得一致的结果。

因此,对于您的价值,您可以 运行 下面找出您实例上所有语言的默认转化价值:

DECLARE Languages CURSOR FOR
SELECT alias
FROM sys.syslanguages;

DECLARE @Alias sysname,
        @SQL nvarchar(MAX);

CREATE TABLE #ConvertedDates (Alias sysname, dt datetime, converted nvarchar(25));

DECLARE @dt datetime = '2020-05-06T00:00:00'

OPEN Languages

FETCH NEXT FROM Languages
INTO @Alias;

WHILE @@FETCH_STATUS = 0
BEGIN

    SET @SQL = N'SET LANGUAGE ' + QUOTENAME(@Alias) + N'; INSERT INTO #ConvertedDates(Alias,dt,converted) VALUES(N' + QUOTENAME(@Alias,'''') + ',@dt,CONVERT(nvarchar(25),@dt));';

    EXEC sys.sp_executesql @SQL, N'@dt datetime', @dt;

    FETCH NEXT FROM Languages
    INTO @Alias;

END;

CLOSE Languages;
DEALLOCATE Languages;

SELECT *
FROM #ConvertedDates;

DROP TABLE #ConvertedDates;

没错,就是Cursor。我想确保每个动态语句 运行 本身,以确保为每次转换保留语言。