2010-06-07 70 views
9

我有一些C代码:函数参数中的预增和后增的操作顺序?

main() 
{ 
    int a=1; 
    void xyz(int,int); 

    xyz(++a,a++);  //which Unary Operator is executed first, ++a or a++? 

    printf("%d",a); 
} 
void xyz(int x,int y) 
{ 
    printf("\n%d %d",x,y); 
} 

功能xyz在,++aa++传递两个参数。有人可以解释操作的顺序来解释结果吗?

上面的代码根据使用的编译器打印“3 13”或“2 23”。

+1

如果您在示例程序中使用了不同的变量,它可能会更清晰。另外,你应该在你正在打印的值之后加上“\ n”*,而不是之前。这将打印“2 23” – DevinB 2010-06-07 13:07:50

+0

你应该尝试一些更清楚。这个语法对于一个人来说很奇怪。简化代码,不要试图编写复杂的东西。 – INS 2010-06-07 14:51:58

回答

26

嗯,有考虑与你的示例代码两件事情:

  1. 的函数参数评价的顺序是不确定的,所以无论是++aa++首先计算是实现相关的。
  2. 多次修改a的值,如果在修改之间没有序列点,则会导致未定义的行为。所以,你的代码的结果是不确定的。

如果我们简化代码并删除不明确的,不确定的行为,那么我们就可以回答这个问题:

void xyz(int x) { } 

int a = 1; 
xyz(a++); // 1 is passed to xyz, then a is incremented to be 2 

int a = 1; 
xyz(++a); // a is incremented to be 2, then that 2 is passed to xyz 
+0

在第二种情况下,函数被调用之前更新了'a'是否为真?我知道*表达式*'++ a'的结果是2,这是传递给'xyz'的结果,但我的理解是副作用可能不一定在函数调用之前应用。 – 2010-06-07 14:58:47

+2

@John:是的:在对函数的所有参数进行评估之后但在函数调用之前有一个序列点。 – 2010-06-07 15:01:38

9

引述Kernighan的&里奇,章节2.12:

中的顺序哪些函数参数 评估没有指定,所以 语句

printf("%d %d\n", ++n, power(2, n)); /* WRONG */ 

可以与 不同的编译器产生不同的结果,具体取决于 在调用 的电源之前n是否递增。该溶液,当然,是 写

++n; 
printf("%d %d\n", n, power(2, n)); 

函数调用,嵌套分配 报表以及增量和 递减运算符原因``侧 效应“” - 一些变量改变 作为副产物评价 的表达。在涉及副作用的任何表达式 中,可能存在 对 中的顺序的微妙依赖性,其中参与 表达式的变量被更新。一个不高兴 情况是由语句

a[i] = i++; 

的问题是,标 是否是我的旧值或新的代表。 编译器可以用不同的方式解释这个问题,并根据它们的解释生成不同的 答案。标准 故意留下大多数此类事项 未指定。当副作用 (赋值给变量)发生时 的表达式由编译器自行决定,因为 的最佳顺序强烈依赖于机器的 体系结构。(该标准并 指定的 参数所有副作用生效称为 函数之前,但不会在通话 帮助上面的printf)的 寓意是写代码 取决于评估的顺序在任何 语言中都是 糟糕的编程习惯。当然,需要 知道需要避免什么,但是如果您不知道如何在各种机器上完成它们,您将不会被诱惑 来利用特定的 实现。一个函数

2

元运算符的评价顺序:

#include <stdio.h> 

void xyz(int x, int y) { 
    printf("x:%d y:%d ", x, y); 
} 

main() { 
    int a; 
    a=1; xyz(++a, a);  printf("a:%d\n", a); 
    a=1; xyz(a, a++);  printf("a:%d\n", a); 
    a=1; xyz(++a, a++);  printf("a:%d\n", a); 
} 

将输出

x:2 y:2 a:2 
x:2 y:1 a:2 
x:3 y:1 a:3 

在我的系统。这表明函数的第二个参数正在被首先评估。您不应该依赖函数参数的评估顺序。它没有定义,所以它在不同的系统上会有所不同。尽管如此,找到这种行为的一个很好的例子还是不错的。

-1

对于非上等运算符,有前增量(++ i)和后增量(i ++)。对于预增量,要增加的值将在操作之前添加。例如:

#include <iostream> 
using namespace std; 

void main() 
{ 
    int i = 0; 
    cout << ++i; 
} 

在这种情况下,输出将是1。变量的“i”是由1的值之前的任何其它操作递增即“清点< < ++ I”。现在

,如果我们这样做了后增量在同一个函数:

#include <iostream> 
using namespace std; 

void main() 
{ 
    int i = 0; 
    cout << i++; 
} 

输出只会是0。这是因为增量会在手术后发生。但既然你想知道在将它们作为参数,这是它怎么会跑到:

#include <iostream> 
using namespace std; 
// Function Prototypes 
void PrintNumbers(int, int); 

void main() 
{ 
    int a = 0, b = 0; 
    PrintNumbers(++a, b++); 
} 

void PrintNumbers(int a, int b) 
{ 
    cout << "First number: " << a << endl; 
    cout << "Second number: " << b << endl; 
} 

当通过这些变量作为参数,输出将是:

First number: 1 
Second number: 0 

我希望这帮助!