[C#, Этюд] expr ? true : false
От: nikov США http://www.linkedin.com/in/nikov
Дата: 16.11.10 17:48
Оценка: 46 (2)
По мотивам http://www.rsdn.ru/forum/dotnet/3765969.1.aspx
Автор: nikov
Дата: 07.04.10


В некоторой программе есть такой statement:

if (/* expression */ ? true : false)
{
    Console.WriteLine(x); // error CS0165: Use of unassigned local variable 'x'
}

, где вместо /* expression */ стоит некоторое выражение. При компиляции программы возникает ошибка, указанная в комментарии.

Если убрать фрагмент

? true : false

, то ошибка исчезает и программа успешно компилируется. Как такое может быть?
Re: [C#, Этюд] expr ? true : false
От: Mab Россия http://shade.msu.ru/~mab
Дата: 16.11.10 22:38
Оценка: 79 (5)
public static void Foo(bool y)
{
  int x;
  if (y && (x = 1) > 0 ? true : false)
  {
    Console.WriteLine(x);
  }
}
Re[2]: [C#, Этюд] expr ? true : false
От: _FRED_ Черногория
Дата: 17.11.10 07:57
Оценка:
Здравствуйте, Mab, Вы писали:

Mab>public static void Foo(bool y)
Mab>{
Mab>  int x;
Mab>  if (y && (x = 1) > 0 ? true : false)
Mab>  {
Mab>    Console.WriteLine(x);
Mab>  }
Mab>}


А из-за чего ошибка появляется?
Help will always be given at Hogwarts to those who ask for it.
Re[3]: [C#, Этюд] expr ? true : false
От: Jack128  
Дата: 17.11.10 08:02
Оценка:
Здравствуйте, _FRED_, Вы писали:

_FR>Здравствуйте, Mab, Вы писали:


_FR>
Mab>>public static void Foo(bool y)
Mab>>{
Mab>>  int x;
Mab>>  if (y && (x = 1) > 0 ? true : false)
Mab>>  {
Mab>>    Console.WriteLine(x);
Mab>>  }
Mab>>}
_FR>


_FR>А из-за чего ошибка появляется?


Я бы спросил, из-за чего она НЕ появляется. && — вроде ленивый, соответственно если y == false, то присваивания не будет -> x — не инициализирован. всегда должна быть ошибка.
Re[4]: [C#, Этюд] expr ? true : false
От: _FRED_ Черногория
Дата: 17.11.10 08:09
Оценка: 8 (1)
Здравствуйте, Jack128, Вы писали:

_FR>>А из-за чего ошибка появляется?


J>Я бы спросил, из-за чего она НЕ появляется. && — вроде ленивый, соответственно если y == false, то присваивания не будет -> x — не инициализирован. всегда должна быть ошибка.


Вот тут:
Mab>>>public static void Foo(bool y)
Mab>>>{
Mab>>>  int x;
Mab>>>  if (y && (x = 1) > 0 /* ? true : false */)
Mab>>>  {
Mab>>>    Console.WriteLine(x);
Mab>>>  }
Mab>>>}

как-раз таки всё понятно: если мы зайдём внутрь if, то переменная [ гарантированно будет инициализорована ("y" должно будет быть истинно).
Help will always be given at Hogwarts to those who ask for it.
Re[3]: [C#, Этюд] expr ? true : false
От: Mab Россия http://shade.msu.ru/~mab
Дата: 17.11.10 09:15
Оценка: 39 (1)
Здравствуйте, _FRED_, Вы писали:

_FR>А из-за чего ошибка появляется?


Потому что так устроена спецификация. Нам нужно, чтобы x была definitely assigned в then-ветке.

5.3.3.5 If statements
For an if statement stmt of the form:
if ( expr ) then-stmt else else-stmt
...
• If v is definitely assigned at the end of expr, then it is definitely assigned on the control flow transfer to then-stmt and to either else-stmt or to the end-point of stmt if there is no else clause.
• If v has the state “definitely assigned after true expression” at the end of expr, then it is definitely assigned on the control flow transfer to then-stmt, and not definitely assigned on the control flow transfer to either else-stmt or to the end-point of stmt if there is no else clause.
...
• Otherwise, v is considered not definitely assigned on the control flow transfer to either the then-stmt or else-stmt, or to the end-point of stmt if there is no else clause.

(Нерелевантные части убраны.)

Итак, после expr-cond ? true : false нужно, чтобы x было definitely assigned или definitely assigned after true expression.

Смотрим дальше:

5.3.3.28 ?: expressions
For an expression expr of the form expr-cond ? expr-true : expr-false:
...
• The definite assignment state of v after expr is determined by:
o If expr-cond is a constant expression (§7.19) with value true then the state of v after expr is the same as the state of v after expr-true.
o Otherwise, if expr-cond is a constant expression (§7.19) with value false then the state of v after expr is the same as the state of v after expr-false.
o Otherwise, if the state of v after expr-true is definitely assigned and the state of v after expr-false is definitely assigned, then the state of v after expr is definitely assigned.
o Otherwise, the state of v after expr is not definitely assigned.

У нас expr-cond не константа и x не является definitely assigned после expr-false. Поэтому срабатывает последний пункт.

Неформальное же объяснение такое: вместо expr-cond ? true : false могло бы быть написано expr-cond ? true : true, и тогда переменная могла бы быть не инициализирована в then-ветке. Однако компилятор не отличает эти два случая, так что приходится пессимизировать ситуацию.
Re[2]: [C#, Этюд] expr ? true : false
От: Mab Россия http://shade.msu.ru/~mab
Дата: 17.11.10 09:21
Оценка:
Здравствуйте, Mab, Вы писали:

Для лучшего понимания полезно ответить (не запуская компилятор) на такой вопрос: что поменяется, если вместо
y && (x = 1) > 0 ? true : false

написать
(x = 1) > 0 && y ? true : false

, а затем понять, отчего так происходит.
Re: [C#, Этюд] expr ? true : false
От: Аноним  
Дата: 17.11.10 12:45
Оценка: -1 :)
Здравствуйте, nikov, Вы писали:

N>По мотивам http://www.rsdn.ru/forum/dotnet/3765969.1.aspx
Автор: nikov
Дата: 07.04.10


А нельзя ли к этюдам етим каких-нибудь картинок с сиськаме добавлять, ато они (этюды) не всем понятны, нов мести с тем хочется быть в общей тусовки. Пасиб
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.