好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

一道笔试指针题目详解

一道笔试指针题目详解

看到本题是在搜狗某年的笔试题上,看也没人给出非常详细的讲解,直接给出了答案,我来尝试写一写,错误之处园友们指教.

貌似本题来源自< The C Puzzle Book> , 搜狗也只是换了一下字符串,直接看题吧

#include <stdio.h>
 char  *c[]={ "  ENTNG  " ,  "  NST  " , "  AMAZI  " , "  FIRBE  "  };
  char ** cp[]={c+ 3 , c+ 2 , c+ 1  , c};
  char  ***cpp=  cp;
  int   main() {
    printf(  "  %s  " ,**++ cpp);
    printf(  "  %s   " ,*--*++cpp+ 3  );
    printf(  "  %s  " ,*cpp[- 2 ]+ 3  );
    printf(  "  %s  " ,cpp[- 1 ][- 1 ]+ 1  );
} 

请写出程序的执行结果....

首先从左到右看:

 char  *c[]=  {
                "  ENTNG  "  , 
                "  NST  "  ,
                "  AMAZI  "  ,
                "  FIRBE  "  
            }; 

*c[] 是一个字符,因此,c[]是指向该字符,c就是一个数组(数组的内容为指向字符的指针),c已经被初始化了.

 char ** cp[]={c+ 3 , c+ 2 , c+ 1 , c};

再看第二行,**cp[]是一个字符,*cp[]就是一个指针,指向该字符,cp[]就是一个指针,指向该指针,而cp就成为了指针数组,内容是指向字符的指针的指针。并且通过c的元素进行了初始化

 char  ***cpp= cp;

第三行,***cpp是一个字符,**cpp指向该字符,*cpp指向该指针,cpp就指向该字符的指针的指针.

然后我画一张图表示初始的情况看看

然后对于下面的输出语句,通过操作符优先级使用括号来区分一下:

*(*(++cpp));

这个嘛,就是把cpp后移(注意cpp已经改变了)然后就指向了cp[1],然后两次取其值即可得到AMAZI

推导过程如下:

++cpp -> cp[ 1 ]        //   cp[1] -> c+2 
++cpp = &cp[ 1 ]        //   &(c+2) 
*++cpp = *(&c+ 2 )      //    c[2] 
**++cpp = *&c[ 2 ]

然后看第二个

(*(--(*(++cpp))))+ 3 ;

加括号后如上,cpp再加一,就指向了cp[2],取一次值(也就是*号)就变成了c[1],然后--c[1]就指向了c[0],取值就成了c[0]的地址,然后地址+3,就是NG了

(*(cpp[- 2 ]))+ 3 ;

上面,cpp指向cp[2]了,然后呢,cpp[-2] 相当于(*cpp)-2,间接引用cp[2],这样cpp[-2]就指向了cp[0]了,然后,就是FIRBE了,加3就是BE了

最后

(cpp[- 1 ][- 1 ])+ 1 ;

cpp还是之前的cp[2],cpp[-1][-1]相当于(*(*cpp)-1)-1),先减1指向了cp[1],取一次值就是c[2]了,然后c[2]-1就成为c[1]了,然后+1之后就是ST了.

所以,最后输出就是

AMAZINGBEST

错误之处还望指正.

 我的博客: http://leaver.me

 

 

分类:  C/C++

作者: Leo_wl

    

出处: http://www.cnblogs.com/Leo_wl/

    

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

版权信息

查看更多关于一道笔试指针题目详解的详细内容...

  阅读:41次