printf("%d, %d\n", i++, ++i)的输出结果是确定的吗???

1. 问题描述

以下代码的输出结果是什么?

题目1:

int i=10;
printf("%d, %d\n", i++, ++i);

题目2:

int i = 3;
printf("%d, %d, %d, %d, %d\n", i++, ++i, i, i++, i);

2. 解题思路【错误】

  printf参数是从右至左入栈的,故:

  • 题目1的输出为:11,12
  • 题目2的输出为:

3. 反思

  • 注意:该类题目编译器不一样,结果就会不一样,即这种行为依赖编译器!!!不必纠结。
  • 原因分析:
    • C/C++语言没有规定具体压栈顺序,没有标准化时C语言支持没有固定参数的函数,所以为了实现这个当时多数编译器都采用从右往左压栈,但是标准化的要求至少有一个固定参数,这个限制就没有必要了。不过从右到左几乎已经成为了C编译器惯用的顺序。C++的_stdcall方式也是采用从右到左,不同的只是不需要调用者自己手动清栈。
    • 另外求值顺序和压栈顺序是两回事,C语言里几乎没有对求值顺序做规定,编译器完全可以先求出值再决定如何压栈。
    • 简单说,这种问题与编译器实现语言的规定有关。不同编译器下生成的代码可能不同,出现的结果就不同。对于这种可能造成错误的代码,不用纠结。

What‘s the value of i++ + i++?
It‘s undefined. Basically, in C and C++, if you read a variable twice in an expression where you also write it, the result is undefined. Don‘t do that. Another example is:

v[i] = i++;

Related example:

f(v[i],i++);

Here, the result is undefined because the order of evaluation of function arguments are undefined.

Having the order of evaluation undefined is claimed to yield better performing code. Compilers could warn about such examples, which are typically subtle bugs (or potential subtle bugs). I‘m disappointed that after decades, most compilers still don‘t warn, leaving that job to specialized, separate, and underused tools.

时间: 2024-08-02 02:51:07

printf("%d, %d\n", i++, ++i)的输出结果是确定的吗???的相关文章

printf格式输出总结

#include<stdio.h>    #include<string.h>    int main()    {        char c, s[20];        int a=1234;       float f=3.141592653589;        double x=0.12345678912345678;        strcpy(s, "Hello,World");        c='\x41';        printf(&q

【转】java格式化输出 printf 例子

[转]java格式化输出 printf 例子 转自http://www.cnblogs.com/TankMa/archive/2011/08/20/2146913.html#undefined import java.util.Date; /** * 使用printf输出 */ /**关键技术点 * 使用java.io.PrintStream的printf方法实现C风格的输出 * printf 方法的第一个参数为输出的格式,第二个参数是可变长的,表示待输出的数据对象 */ public clas

C语言第一课--printf()输出数据

1 #include<stdio.h> 2 3 int main() 4 { 5 //输出数字 6 printf("%d\n",1+2); // 1 7 printf("%d\n",3-4); // 2 8 9 printf("%d\n",5*6); // 3 10 printf("%d\n",8/4); // 4 --- 思考与 6的差别 11 12 printf("%d\n",8./5.);

printf(&quot;%d&quot;,5.01)和printf(&quot;%f&quot;,5)的输出结果

printf("%f\n",5); printf("%d\n",5.01); printf("%f\n", (float)5); printf("%f\n", 5.f); out:0.00000018897856105.0000005.000000看到结果,会感觉非常奇怪.1处怎么会输出0呢?2又为何会显示这么大的一个数呢?解释:下面是转自网上的一篇博客的解释1,之所以没输出5,这是C语言设计的原因.2,之所以输出0,这是计算

C语言中printf的规范输出

1.调用格式为  printf("<格式化字符串>", <参量表>);   其中格式化字符串包括两部分内容: 一部分是正常字符, 这些字符将按原样输出; 另一部分是格式化规定字符, 以"%"开始, 后跟一个或几个规定字符, 用来确定输出内容格式.参量表是需要输出的一系列参数, 其个数必须与格式化字符串所说明的输出参数个数一样多, 各参数之间用","分开, 且顺序一一对应, 否则将会出现意想不到的错误. 2.格式化字符 %d

shell之 printf 输出语句

总结: (1)printf 使用引用文本或空格分隔的参数,外面可以在printf中使用格式化字符串,还可以制定字符串的宽度.左右对齐方式等.默认printf不会像 echo 自动添加换行符,我们可以手动添加 \n. (2)%-10s 指一个宽度为10个字符(-表示左对齐,没有则表示右对齐),任何字符都会被显示在10个字符宽的字符内,如果不足则自动以空格填充,超过也会将内容全部显示出来. printf 命令模仿 C 程序库(library)里的 printf() 程序. (3)格式化输出,加双引号

[Linux]Linux printf 输出重定向【转】

转自:http://www.cnblogs.com/aaronLinux/p/6765145.html?utm_source=itdadao&utm_medium=referral 方法一 #include <stdlib.h> #include <stdio.h> #include <unistd.h> #include <sys/stat.h> #include <fcntl.h> int main() { fflush(stdout

c语言的printf输出浮点数的一些问题

在printf时:如果以%f格式输出,将输出8个字节(scanf输入时,%f是4个字节) 在参数入栈时如果是float型或者double型 直接入栈8个字节,此时输出及后续输出都没问题 但如果参数小于8个字节且不是float型:比如int   shor int  ,就会扩展符号位,成为4个字节再入栈,但是输出的是8个字节,所以会读取其他参数的入栈结果 #include <stdio.h> #include <stdlib.h> #include <string.h> i

为什么printf()用%f输出double型,而scanf却用%lf呢?

转:https://blog.csdn.net/bat67/article/details/52056057 示例:double x:scanf(“%f”,&x):输入“123.4”,输出x的值结果为0,没有接收输入的数据,再输入别的数据,结果都为0.这是因为用户定义x为双精度型数据,而用“%f”格式输入数据,仍不能接收,应该使用“%lf”或“%le”,即scanf(“%lf”,&x):此时输入“123.4”即可接收.因此长整型数据和双精度型数据必须使用附加格式说明字符l,短整型数据必须使