2013-08-29 11 views
7

To kolejna sekwencja punkt pytanie, ale raczej prosty:Punkt kolejności od wywołania funkcji?

#include <stdio.h> 
void f(int p, int) { 
    printf("p: %d\n", p); 
} 

int g(int* p) { 
    *p = 42; 
    return 0; 
} 

int main() { 
    int p = 0; 
    f(p, g(&p)); 
    return 0; 
} 

Czy to niezdefiniowane zachowanie? Czy też wywołanie g(&p) działa jako punkt sekwencyjny?

Odpowiedz

9

Nie. Nie wywołuje ona zachowania niezdefiniowane. Jest to po prostu nieokreślony, ponieważ kolejność, w jakiej oceniane są argumenty funkcji, nie jest określona w Standardzie. Więc wynik może być 0 lub 42 w zależności od kolejności oceny ustalonej przez twój kompilator.

+6

Pytanie także pyta, czy 'g (& p)' działa jako punkt sekwencyjny. W ocenie 'g (& p)' występują dwa punkty kolejności: Pomiędzy oceną 'g' a oceną' & p' oraz między oceną "pełnych wyrażeń" '* p = 42;' oraz '0' w' return'. Ale żaden z nich nie nakazuje oceny argumentu 'p' w odniesieniu do oceny' g (& p) '. –

+0

@EricPostpischil: Świetny komentarz. :-) – Nawaz

4

Zachowanie programu jest nieokreślony, ponieważ nie wiemy, kolejność oceny argumentów funkcji, z draft C++ standard1.9Programu wykonania ustępu 3:

Niektóre inne aspekty i operacje abstrakcyjna maszyna jest opisana w tym międzynarodowym standardzie jako nieokreślona (na przykład kolejność oceny argumentów funkcji). Tam, gdzie jest to możliwe, niniejszy Międzynarodowy Standard definiuje zbiór dozwolonych zachowań. [...]

i wszystkie efekty uboczne argumentów sekwencjonuje zanim funkcja zostanie wprowadzony, z sekcji 5.2.2Funkcja połączeń ustęp 8:

[Uwaga: oceny z Postfix wyrażenie i wyrażeń argumentów są wszystkie w stosunku do siebie. Wszystkie skutki uboczne ocen ekspresji argumentu są sekwencjonowane przed wprowadzeniem funkcji (patrz 1.9). -end uwaga]

chodzi o C oba punkty są pokryte w C99 draft standard w sekcji 6.5.2.2 wzywa Funkcja pkt 10:

Kolejność oceny desygnatora funkcji, rzeczywiste argumenty i Podwyrażenia w rzeczywistych argumentach są nieokreślone, ale przed rzeczywistym połączeniem istnieje punkt sekwencji .

więc zarówno CC++ i może skończyć się albo f(0,0) lub f(42,0).

Powiązane problemy