This code works ok:
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;
output:
fk          maxx
----------- -----------
1           NULL
with:
Warning: Null value is eliminated by an aggregate or other SET operation.
But this code:
select fk, max(a) maxx
    from (values(1, null), (1, null)) x(fk, a)
    group by fk;
give error:
Msg 8117, Level 16, State 1, Line 5
Operand data type NULL is invalid for max operator.
In both cases sql server calculate max from null and null? Isn't it?
In the first case you implicitly specify a datatype, namely an integer. This is inferred from the then which will never be reached. The fact that the then will not be executed, doesn't matter for sql server. In fact, the way sql server determines the return type: "the highest precedence type from the set of types in result_expressions and the optional else_result_expression". So the return type is chosen before actual execution, from all potential datatypes to be returned in the then and else. in other words, before sql server 'realises' that some statements cannot possibly be reached.
Since the datatype is known, max can be applied.
In the second case you don't specify a datatype, so sql server can not know how to implement the max. A max for varchar is different than a max for integers.
That is neat. In my opinion it probably should be implicitly converted to int.
The docs mention this for inserts:
the values specified in a multi-row
insertstatement follow the data type conversion properties of theunion allsyntax. - Table Value Constructor (Transact-SQL)
Both of these turn the null value to an 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 demo: http://rextester.com/VWMT9189
returns
+-----------+------+
|   name    | name |
+-----------+------+
| MyNullCol | int  |
| a         | int  |
+-----------+------+
                        If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With