Тип условного выражения не может быть определен, потому что нет никакого неявного преобразования между 'int' и <null>

Почему это не компилируется?

int? number = true ? 5 : null;

Тип условного выражения не может быть определен, потому что нет никакого неявного преобразования между 'int' и <null>

Ответ 1

В спецификации (§7.14) сказано, что для условного выражения b ? x : y существует три возможности: либо x, и y оба имеют тип и некоторые хорошие условия удовлетворяются, только один из x и y имеет тип и выполняются определенные хорошие условия, или возникает ошибка времени компиляции. Здесь "определенные хорошие условия" означают определенные преобразования, которые мы рассмотрим ниже.

Теперь перейдем к германной части спецификации:

Если только один из x и y имеет тип, и оба x и y неявно конвертируются в этот тип, то это тип условного выражения.

Проблема здесь в том, что в

int? number = true ? 5 : null;

только один из условных результатов имеет тип. Здесь x - это литерал int, а y - null, который не имеет типа , а null неявно конвертируется в int 1. Поэтому "определенные хорошие условия" не выполняются, и возникает ошибка времени компиляции.

Существует два способа:

int? number = true ? (int?)5 : null;

Здесь мы все еще находимся в том случае, когда только один из x и y имеет тип. Обратите внимание, что null все еще не имеет типа, но компилятор не будет иметь никаких проблем с этим, потому что (int?)5 и null оба неявно конвертируются в int? (§6.1.4 и §6.1.5).

Другим способом, очевидно, является:

int? number = true ? 5 : (int?)null;

но теперь мы должны прочитать другое предложение в спецификации, чтобы понять, почему это нормально:

Если x имеет тип x и y имеет тип y, то

  • Если неявное преобразование (§6.1) существует от x до y, но не от y до x, то y является типом условного выражения.

  • Если неявное преобразование (§6.1) существует от y до x, но не от x до y, то x является типом условного выражения.

  • В противном случае тип выражения не может быть определен, и возникает ошибка времени компиляции.

Здесь x имеет тип int и y имеет тип int?. Нет неявного преобразования из int? в int, но есть неявное преобразование от int до int?, поэтому тип выражения int?.

1: Обратите внимание, что тип левой части игнорируется при определении типа условного выражения, что является общим источником путаницы.

Ответ 2

null не имеет идентифицируемого типа - ему просто нужно немного подталкивать, чтобы сделать его счастливым:

int? number = true ? 5 : (int?)null;