操作数数据类型 NULL 对于最大运算符无效



这段代码工作正常:

select fk, max(case when 1 = 0 then 1 else null end) maxx
from (values(1, null), (1, null)) x(fk, a) 
group by fk;

输出:

fk          maxx
----------- -----------
1           NULL

跟:

Warning: Null value is eliminated by an aggregate or other SET operation.

但是这个代码:

select fk, max(a) maxx
from (values(1, null), (1, null)) x(fk, a)
group by fk;

给出错误:

Msg 8117, Level 16, State 1, Line 5 Operand data type NULL is invalid for max operator.

在这两种情况下,sql 服务器都会从nullnull中计算max?不是吗?

在第一种情况下,你隐式指定一个数据类型,即一个整数。这是从永远不会达到的then推断出来的。then不会被执行的事实对于 sql 服务器来说并不重要。事实上,sql Server 确定返回类型的方式是:">result_expressions中的类型集中优先级最高的类型以及可选的else_result_expression"。因此,返回类型是在实际执行之前thenelse中返回的所有潜在数据类型中选择的。换句话说,在SQL Server"意识到"某些语句不可能被访问之前。

由于数据类型是已知的,因此可以应用max

在第二种情况下你没有指定数据类型,所以sql服务器不知道如何实现maxvarcharmax不同于整数的max

这很整洁。在我看来,它可能应该隐式转换为int.

文档在inserts中提到了这一点:

多行insert语句中指定的值遵循union all语法的数据类型转换属性。 - 表值构造函数 (事务处理-SQL)


两者都将null值转换为int

select null as MyNullCol
into dbo.tmp
union all 
select null as MyNullCol
select fk, a
into dbo.tmp2
from (values(1, null), (1, null)) x(fk, a)
select c.name, t.name
from sys.columns c
inner join sys.types t
on c.user_type_id = t.user_type_id
where c.name in ('a','mynullcol')

Rextester 演示:http://rextester.com/VWMT9189

返回

+-----------+------+
|   name    | name |
+-----------+------+
| MyNullCol | int  |
| a         | int  |
+-----------+------+

最新更新