Пример порядка оценки

Я пытаюсь вспомнить раз и навсегда, как оцениваются выражения. И с этим моим заданием я придумал этот пример, из которого я не знаю, что делать.

#include <iostream>
using namespace std;
typedef void(*func)(int);

void r( int i )
{
cout << i << endl;
}
func f( int i )
{
cout << i << endl;
return &r;
}

int main()
{
int i = 0;
f(++i)(++i);
return 0;
}

Если этот фрагмент кода скомпилирован с помощью MVSC 2008, будет получен следующий вывод: 2 2. Тот же код, но скомпилированный с помощью gcc 4.8.1 вызовет предупреждение (операция над i может быть неопределенной) и выдаст такой вывод: 1 2.

Я пытаюсь понять, почему gcc 4.8.1 считает, что может быть случай неопределенного поведения? Побочные эффекты обоих предварительных приращений упорядочены относительно друг друга.

Ура,
Андрей

2

Решение

Побочные эффекты обоих предварительных приращений упорядочены относительно друг друга.

Нет, они не. Оценка каждого аргумента выполняется перед вызовом его функции, а вызовы функций — друг над другом; но оба могут быть оценены перед первым вызовом, и в этом случае нет ничего, чтобы связать их друг с другом.

7

Другие решения

это зависит от того, что вы подразумеваете под «предварительным приращением» … вы читаете это так:

  ++i
f(i)
++i
f (i) (i)

Но вы могли бы так же легко сделать это:

 ++i
++i
f(i)
f(i) (i)

Я не думаю, что спецификация требует того или иного способа.

2

По вопросам рекламы [email protected]