Tytuł pytania mówi wszystko: czy deklaracje formularza int a = 0, b = a
mają niezdefiniowane zachowanie?Czy `int a = 0, b = a` ma niezdefiniowane zachowanie?
Odpowiedz
Nie, to jest dobrze zdefiniowane. Jest to deklaracja z dwoma deklaratorami: a
i b
. Każdy deklarator ma inicjator.
Każdy startowe declarator w zgłoszeniu analizowano osobno, jak gdyby była w zgłoszeniu sama.
Oznacza to, że linia jest traktowany jak:
int a = 0;
int b = a;
"analizowane osobno" nie wskazuje nic na sekwencjonowanie w oświadczeniu o wykonaniu. Czy jest o to silniejsze wskazanie w standardzie? –
Aby odpowiedzieć na własne uwagi, myślę, że trzeba zacytować 1.9/14 na temat oceny pełnych wyrażeń, które są sekwencjonowane przed oceną kolejnych pełnych wyrażeń. Zobacz komentarz do http://stackoverflow.com/a/6414247/19563. –
Nie, nie ma Undefined Behavior.
za § 8/3 z C++ 11 Standard:
Każdy startowe declarator w zgłoszeniu są analizowane osobno, jak gdyby była w zgłoszeniu sam
Również jako stopki 97 określa:
zgłoszenie kilka declarators zwykle równoważna odpowiedniej sekwencji zgłoszeń każdy z jednym deklaratorem . Oznacza to
T D1, D2, ... Dn;
zazwyczaj (*) równoważne
T D1; T D2; ... T Dn;
Oznacza to, że a
jest inicjowana, następnie b
inicjowany jest i przyjmuje wartości z a
. Zauważ również, że nawet jeśli tak nie było, to istnieje quite a long debate on SO, czy to byłoby UB, czy nie, i osiągnięto konsensus w sprawie tego, że nie jest to UB.
(*): Jak wyjaśnia Olaf DIETSCHE w komentarzach, sytuacje, w których równoważność ta robi nie chwyt są wymienione później w tym samym przypisie.
Przypisy nie są normatywne w normie ISO, więc nie określają niczego, są jedynie tekstem informacyjnym. – Lundin
Oprócz tego, co powiedział Lundin, słowo "zwykle" nie daje mi żadnych ciepłych uczuć o gwarancji sekwencji. – IronMensan
@Lundin: Przypisy nie są normatywne, to prawda. Ale często są tam po to, aby wskazać rzeczy, które można inaczej wywnioskować ze Standardu poprzez bardziej złożone formalne odliczenia. Nie byłem w stanie przeprowadzić tych dedukcji osobiście, ale myślałem, że może to być odpowiednie odniesienie, przynajmniej jako deklaracja zamiaru. –
Następne pytanie brzmi, czy taki wiersz kodu ma sens w jakimkolwiek realnym scenariuszu? Czy istnieje jakikolwiek powód, dla którego napiszesz to, a nie 'int a = 0; int b = 0; '? – Lundin
@Lundin Gdy wartość 'a' jest wynikiem funkcji, której nie chcesz wykonywać dwukrotnie, co jest moim przypadkiem. Potrzebuję dwóch kopii tej wartości: jednej do wyprowadzenia i jednej, którą muszę zmodyfikować podczas wykonywania innych obliczeń. –
możliwy duplikat [Czy przecinek na liście zmiennych jest punktem sekwencyjnym?] (Http://stackoverflow.com/questions/6414030/is-the-comma-in-a-variable-list-a-sequence-point) i [Czy kolejność przypisywania na liście inicjalizowanych zmiennych jest niezdefiniowana?] (http://stackoverflow.com/questions/12729962/jest-pokazanie-w-listowaniu-instruowanych-zmiennych -undefined? lq = 1) ... –