zoukankan      html  css  js  c++  java
  • printf问题参数顺序

    #include <stdio.h>
    int main(int argc, char *argv[])
    {
    	int b = 3;
    	int arr[] = { 6, 7, 8, 9, 10};
    	int *ptr = arr;
    	*(ptr++)  += 123;
    	printf( "%d, %d\n", *ptr, *(++ptr) ); 
    	return 0;
    }

    求输出结果?
    开始看这个题目觉得很简单的,无非就是考i++和++i的问题,后来发现,在printf那里出问题了,我以为参数是按照stdcall顺序的,即从左到右,
    可结果确实从右到左,查阅资料表明,C语言里面的函数参数入栈都是从右到左的顺序(之前忘记了,汗~~~),究其原因。看到某篇文章,称那
    是因为C语言支持不定参数而要求这样做的,因为这样的话,右边的参数先入栈,在栈底,而左边的却在栈顶,调用参数的话就只需要从栈依
    次取出即可,而不需要参数个数。倘若参数入栈是从左到右,那么在遇到动态参数个数的问题时,由于函数调用的参数个数是不确定的,所以
    对于取参数就遇到了不好处理的问题了,因为不知道栈顶的那个参数对应于函数的哪个参数,而如果采用参数从右到左顺序的话,那么就不需
    要知道参数个数,直接从栈里取参数,然后和函数里面的参数从左到右匹配即可。这种解释,我觉得还是很不错的。
    回到本题来,因为入栈是从右到左的,所以先会执行++ptr操作,然后把此时的数据值入栈,然后把左边的*ptr入栈,这时的ptr已经自增了,所以
    本题的答案是:8, 8
    事实发现当采用如下方式输出时:
    printf( "%d, %d, %d\n", *ptr, *(++ptr), *ptr ); 

    结果是:8, 8, 7
    补充一点,由于printf采用的是动态参数个数,当采用如下方式输出数据时:
    printf( "%d, %d", 1, 3, 5); 

    输出结果是:1, 3
    表明printf摒弃了后面的5,即print根据格式字符串决定输出,然后按照格式字符串的规则,对于函数参数从左到右匹配,如果匹配完了之后还剩
    下其他参数,那么函数将会摒弃这些参数。
    附:好久没认真学习过C语言了,忘记了许多东西,现在复习起来真有点惭愧。
  • 相关阅读:
    Tomcat中的类是怎么被一步步加载的?
    Tomcat中的类是怎么被一步步加载的?
    Tomcat中的类是怎么被一步步加载的?
    redis- info调优入门-《每日五分钟搞定大数据》
    redis- info调优入门-《每日五分钟搞定大数据》
    redis- info调优入门-《每日五分钟搞定大数据》
    Lambda表达式详解
    2012年末工作中遇到的问题总结及感悟
    数据库表扩展字段设计思路
    数据库表扩展字段设计思路
  • 原文地址:https://www.cnblogs.com/arbboter/p/4225277.html
Copyright © 2011-2022 走看看