Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/25.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql server 为什么T-SQL ISNULL()会截断字符串,而COALESCE不会?_Sql Server_Tsql_Coalesce_Isnull_Truncation - Fatal编程技术网

Sql server 为什么T-SQL ISNULL()会截断字符串,而COALESCE不会?

Sql server 为什么T-SQL ISNULL()会截断字符串,而COALESCE不会?,sql-server,tsql,coalesce,isnull,truncation,Sql Server,Tsql,Coalesce,Isnull,Truncation,鉴于以下情况: SELECT ISNULL('XY' + NULL, 'ABCDEFGHIJ') -- Outputs ABC (Why?) SELECT COALESCE('XY' + NULL, 'ABCDEFGHIJ') -- Outputs ABCDEFGHIJ 为什么这些语句返回不同的结果?ISNULL()将替换值转换为检查表达式的类型。在这种情况下,检查表达式的类型是CHAR(2),因此转换替换值会截断它(您确定得到的是ABC,而不仅仅是AB?) 来自微软: 如果替换值比检查表达式

鉴于以下情况:

SELECT ISNULL('XY' + NULL, 'ABCDEFGHIJ') -- Outputs ABC (Why?)
SELECT COALESCE('XY' + NULL, 'ABCDEFGHIJ') -- Outputs ABCDEFGHIJ
为什么这些语句返回不同的结果?

ISNULL()
将替换值转换为检查表达式的类型。在这种情况下,检查表达式的类型是
CHAR(2)
,因此转换替换值会截断它(您确定得到的是
ABC
,而不仅仅是
AB
?)

来自微软:

如果
替换值
检查表达式
长,则可以截断
替换值

根据Microsoft的说法,对于功能:

ISNULL(check_expression, replacement_value)
replacement\u value
的类型必须隐式转换为
check\u表达式的类型。请注意,
'xy'+NULL
的类型是
VARCHAR(3)
。因此,您的字符串
'ABCDEFGHIJ'
被转换为
VARCHAR(3)
,并因此被修剪

这听起来很奇怪,为什么它不是
VARCHAR(2)
,但它是这样的-比
'xy'长一个字符。您可以使用此并亲自查看
'xy'+NULL
的类型与表达式
的类型相同,当1=2,然后是'XYZ'ELSE NULL END
,它是
NULL
,但与
VARCHAR(3)
隐式兼容


对于表达式
'xy'+NULL
而言,可以将感知长度计算为
'xy'
字符串长度(2)加上每添加一个
NULL
。例如,
'xy'+NULL+NULL
的类型是
VARCHAR(4)
'xy'+NULL+NULL+NULL
的类型是
VARCHAR(5)
等等-查看此。这非常奇怪,但这就是MS SQL Server 2008和2012的工作原理。

您可以在此处查看所有差异,非常清楚

MSDN:


MSDN博客:

很好的解释,尽管我不相信varchar(3)而不是varchar(2)-我在任何地方都找不到它的文档。我必须增加这里的信息,以解释更多关于合并行为而不是ISNULL行为的信息,来自Microsoft:合并表达式是大小写表达式的语法快捷方式。也就是说,查询优化器将代码COALESCE(expression1,…n)重写为以下CASE表达式:CASE WHEN(expression1不为NULL)然后expression1 WHEN(expression2不为NULL)然后expression2。。。ELSE expressionN END->case返回类型由最高的expr优先级给出。这解释了
合并
行为,但没有说明
'xy'+NULL
的类型是
VARCHAR(3)
的原因。这一定与SQL Server内部结构有关。我不确定是否能从您的示例中得到证据。第二个查询是因为“XYZ”而不是因为NULL而成为varchar(3)的情况,对吗?所以我猜剩下的疑问是“X”+NULL是否会变成varchar(2)而不是varchar(1)。那么,在这种情况下NULL是否被视为单个字符?在使用ISNULL连接字符串时,我是否需要担心溢出/截断?是的,NULL将再添加1个字符。这非常奇怪,但这里有一个明确的证据:+1对于这篇博文,我在第一次研究中没有注意到。很好的资源。