您能解释这些输出吗?

1)

char s[]="TvNnFs",*p;
for(p=&s[5];p>=s;p--)
    --*p;
puts(s);


输出:SuMmEr

2)

char s[]="TvNnFs",*p;
for(p=&s[5]; p>=s; p--)
    ((--*p)<'a') ? (*p+=('a'-'A')) : (*p);
puts(s);


输出:夏季

最佳答案

这个

char s[]="TvNnFs",*p;


其中s是字符数组,而p是字符指针,如下所示

 s[0]  s[1]   s[2]  s[3]  s[4]  s[5]  s[6]
  ------------------------------------------
 |  T  |  v  |  N  |  n  |  F  |  s  |  \0  |
  ------------------------------------------
 s 0x100 0x101 0x102 0x103 0x104 0x105 0x106.. (assume 0x100 is base address of s)


接下来,for循环

for(p=&s[5];p>=s;p--)
    --*p;


此处p=&s[5]指针p指向s[5]的地址,即0x105。接下来是p>=s,即0x105 >= 0x100为真,然后--*p执行,即第一个*p,这意味着0x105内存位置中的值是s,并对该值进行减法运算将使s[5]成为r

现在char数组s看起来像

 s[0]  s[1]   s[2]  s[3]  s[4]  s[5]  s[6]
  ---------------------------------------------
 |  T  |  v  |  N  |  n  |  F  |  r(new)|  \0  |
  ---------------------------------------------
 s 0x100 0x101 0x102 0x103 0x104 0x105 0x106..


注意:您可能想知道通过执行--*p s如何受到影响?这是因为p指向或持有s的地址,即*p所做的任何更改都会间接影响s

p--发生之后,即p现在指向的位置比在0x104之前的位置早。直到p到达s0x100 >= 0x100之前,将进行相同的操作。最终char数组s看起来像

      s[0]  s[1]   s[2]  s[3]  s[4]  s[5]  s[6]
      -------------------------------------------
     |  S  |  u  |  M  |  m  |  E  |  r  |  \0  |
      -------------------------------------------
     s 0x100 0x101 0x102 0x103 0x104 0x105 0x106..


因此它打印SuMmEr

情况2:

char s[]="TvNnFs",*p;
for(p=&s[5]; p>=s; p--)
((--*p)<'a')?(*p+=('a'-'A')):(*p);
puts(s);


这里

       s[0]  s[1]   s[2]  s[3]  s[4]  s[5]  s[6]
      ------------------------------------------
     |  T  |  v  |  N  |  n  |  F  |  s  |  \0  |
      ------------------------------------------
     s 0x100 0x101 0x102 0x103 0x104 0x105 0x106..
                                      |
                                      p points here


对于0x105 >= 0x100:这个

((--*p)<'a')?(*p+=('a'-'A')):(*p);


是三元运算符,即首先执行((--*p)<'a'),如果结果为true,则将输出(*p+=('a'-'A')),否则为(*p)。因此,这里看起来像((--*p)<'a'),即'r' < 'a'是错误的,因此只是(*p),但是s[5]在此之后由于--*p而被更改。

      s[0]  s[1]   s[2]  s[3]  s[4]  s[5]  s[6]
      ------------------------------------------
     |  T  |  v  |  N  |  n  |  F  |  r  |  \0  |
      ------------------------------------------
     s 0x100 0x101 0x102 0x103 0x104 0x105 0x106..
                                |
                                p points here due to p--


接下来,对于0x104 >= 0x100

((--*p)<'a')?(*p+=('a'-'A')):(*p);


'E' < 'a'70 < 97这是正确的,因此该(*p+=('a'-'A'))被执行,即

*p = *p + ('a' - 'A')
   = 'E' + (97 - 65)
   = 'E' + 32
*p = 'e' /* now s[4] overwritten by e(previously F) */


现在数组看起来像

   s[0]  s[1]   s[2]  s[3]  s[4]  s[5]  s[6]
  ------------------------------------------
 |  T  |  v  |  N  |  n  |  e  |  r  |  \0  |
  ------------------------------------------
 s 0x100 0x101 0x102 0x103 0x104 0x105 0x106..
                      |
                      p points here due to p--


直到0x100 >= 0x100为止,相同的操作都会继续进行。

关于c - C. for循环与字符,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/55282981/

10-11 15:37