Това недефинирано поведение ли е в C/C++

int foo(int c){
    return c;
}

int main(void){
    int a=5,c;
    c = foo(--a) + a; 
}

Ще извика ли недефинирано поведение в C/C++? Мисля, че няма да стане.

След като прочетох всички отговори, не мога да разбера дали това е недефинирано поведение или неопределено поведение.


person jaya    schedule 22.03.2011    source източник
comment
Не, няма, защото няма да се компилира. (Къде е точката и запетая!)   -  person flight    schedule 22.03.2011
comment
stackoverflow.com/questions/4176328/ има много информация за това.   -  person Steve Jessop    schedule 22.03.2011
comment
Освен ако не внедрявате компилатор или комплект за тестване на компилатор, или вашата компания не наема куп езикови адвокати, бих поставил под съмнение необходимостта ви дори да знаете това. Да, тук в SO има няколко души, които могат да отговорят на този въпрос (и ще намерите повече на comp.lang.c++.moderated и comp.std.c++ в Usenet), но не са много и дори те понякога не са съгласни по тънки ъглови случаи. Още по-важното е, че (някои) компилатори също може да не са съгласни с тях. Ако кодът не е достатъчно ясен, че с един поглед към него програмист с разумен опит може да каже Да! или Не!, опростете го и готово.   -  person sbi    schedule 22.03.2011
comment
Отговорих грешно, за да докажа нещо :)   -  person Matt Joiner    schedule 22.03.2011
comment
@Matt: отговорът ти ме изненада! Накара ме да скоча в моето копие на FCD, за да проверя дали не съм пропуснал нещо! @Erik обаче ни покрива :)   -  person Matthieu M.    schedule 22.03.2011


Отговори (5)


Да, това е недефинирано поведение - a и foo(--a) могат да бъдат оценени в произволен ред.

За допълнителна справка вижте напр. Точка на последователността. Има точка на последователност след пълния израз и след оценка на аргумента към foo - но редът на оценка на подизразите е неуточнен за 5/4:

Освен където е отбелязано, редът на оценка на операндите на отделните оператори и подизразите на отделните изрази, както и редът, в който възникват страничните ефекти, не е уточнен. Между предишната и следващата точка на последователност, съхранената стойност на скаларния обект трябва да бъде променена най-много веднъж чрез оценката на израз. Освен това, предходната стойност трябва да бъде достъпна само за определяне на стойността, която да бъде съхранена. Изискванията на този параграф трябва да бъдат изпълнени за всяко допустимо подреждане на подизразите на пълен израз; в противен случай поведението е недефинирано.

РЕДАКТИРАНЕ: Както Prasoon посочва, поведението е неуточнено поради реда на оценката ... е неуточнено. и става недефинирано поради предходната стойност ще бъде достъпна само за определяне на стойността, която да бъде съхранена

person Erik    schedule 22.03.2011
comment
Доколкото мога да разбера, е още по-лошо. Нищо не би попречило a да бъде оценено след --a, но преди foo(...), което може да има значение, ако foo допълнително промени стойността на a. - person Matthieu M.; 22.03.2011
comment
@Eric : Това не е единствената причина. Например int c = foo(k--) + foo(--j) не извиква undefiend поведение, въпреки че редът на оценка на + не е определен. - person Prasoon Saurav; 22.03.2011
comment
@Eric: Поведението е не само неуточнено, но е и недефинирано. Прочетете отговора ми. :) - person Prasoon Saurav; 22.03.2011

Трябва да прочетете това, то ще ви каже, че вашият код е недефиниран, защото + не е точка на последователност и като такова не е дефинирано дали първо се оценява f(--a) или a.

person filmor    schedule 22.03.2011
comment
Или прочетете отличния запис с често задавани въпроси по въпроса. - person sbi; 22.03.2011

Въпреки че операндите на оператора + могат да бъдат оценени в който и да е ред, поведението е недефинирано, защото нарушава второто правило

1) Между предишната и следващата точка на последователност даден обект трябва да има своята съхранена стойност, променена най-много веднъж чрез оценката на израз.

2) Освен това, предходната стойност ще бъде достъпна само за определяне на стойността, която да бъде съхранена.

Следното е добре дефинирано

c = foo(a-1) + a ;

Прочетете този ЧЗВ запис за по-добро разбиране на недефинирано поведение и точки на последователност.

person Prasoon Saurav    schedule 22.03.2011

Според Wikipedia + не е точка на последователност, така че редът на оценката не е фиксирана, следователно имате недефинирано поведение.

person Björn Pollex    schedule 22.03.2011
comment
Използвайте думата оценка вместо изпълнение - person Prasoon Saurav; 22.03.2011

Ще получите предупреждение за върнат тип в основната функция, иначе е добре и c = 8 в края на main().

person Hiren    schedule 22.03.2011
comment
... не, няма и не е задължително. - person flight; 22.03.2011
comment
да, съгласен съм, че не е задължително. Имах предвид, че може да получите - person Hiren; 22.03.2011
comment
-1 - това не е правилно - прочетете точките на последователността: en.wikipedia.org/wiki/Sequence_point - person Paul R; 22.03.2011