Переписывание сложения как унарного выражения

#c #compilation

#c #Сборник

Вопрос:

Я наткнулся на следующее утверждение:

Умный компилятор может распознать, что x = x 1 может обрабатываться так же, как x .

Почему здесь вместо оператора post-fix используется префиксный оператор (или любой другой, если это не имеет значения)? Например, если бы у меня был следующий цикл:

 while (x < 10) {
    ...
    x  ; // wouldn't this be the same as doing   x here?
}
 

Какой был бы случай, который показывает, как x = x 1 эквивалентно x и нет x ?

Ответ №1:

Вот простой пример. Предположим, у вас есть что-то вроде этого:

 a = (x = x   1);
 

Это было бы эквивалентно

 a =   x;
 

но не для

 a = x  ;
 

Ответ №2:

Какой был бы случай, который показывает, как x = x 1 эквивалентно x, а не x ?

Любой случай, когда используется значение выражения.

Один пример: if((x = x 1) < 10) эквивалентно if( x < 10) , но нет if(x < 10) .

Ответ №3:

Не имеет значения, используете ли вы i или i как отдельное выражение. Единственное различие заключается в значении выражения, которое не используется в обоих случаях.

Вы также можете написать i = 1 или i = i 1 , и компилятор должен сгенерировать один и тот же код для всех 4 вариантов (с включенной оптимизацией).

Если используется значение выражения, i = i 1 и i = 1 эквивалентны i и все имеют обновленное значение, тогда i как имеет исходное значение i .

Комментарии:

1. «Неиспользуемый в обоих случаях» или «не используется ни в одном случае» было бы лучше. Формулировка «не используется в обоих случаях» предполагает, что оно используется или, по крайней мере, может использоваться в одном из случаев.

2. @JohnBollinger: спасибо, действительно, была третья возможная интерпретация, которая была непреднамеренной 🙂

Ответ №4:

Выражение i возвращает значение i перед его увеличением, в то время как выражение i возвращает значение i после увеличения.

Например:

 int i = 1;
int j = i  ; // j now equals 1, i equal 2
 

И i

 int i = 1;
int j =   i; // j and i both equal 2.
 

Выражение x = x 1 возвращает значение x после увеличения, а не перед ним, поэтому оно эквивалентно i