C中带指针的For循环

C中带指针的For循环,c,arrays,string,pointers,for-loop,C,Arrays,String,Pointers,For Loop,我不明白指针在for循环中的作用。*p在以下循环中做什么 我确实理解其余的,但是为什么*p不像p>3或者类似的东西呢? 为什么只有它? 为什么是这样写的?它利用了一个事实,即字符串的终止符(最终由for循环找到)将是一个ASCIINUL,它是一个零,也恰好计算为false,从而终止for循环 值得注意的是0、false、NULL和ASCII-NUL之间的区别和相似性。请参阅此问题:在布尔上下文中,例如for循环的条件,C中的每个表达式的计算结果为true(非零)或false(零) 您希望for循

我不明白指针在
for
循环中的作用。
*p
在以下循环中做什么

我确实理解其余的,但是为什么
*p
不像
p>3
或者类似的东西呢?
为什么只有它?

为什么是这样写的?

它利用了一个事实,即字符串的终止符(最终由for循环找到)将是一个ASCII
NUL
,它是一个零,也恰好计算为false,从而终止for循环


值得注意的是0、false、NULL和ASCII-NUL之间的区别和相似性。请参阅此问题:

在布尔上下文中,例如
for
循环的条件,C中的每个表达式的计算结果为true(非零)或false(零)

您希望
for
循环在到达字符串末尾时终止


在C语言中,每个字符串都以字符
'\0'
结尾,实际上是
0
。因此,当
for
循环到达字符串末尾时,
*p
计算结果为
'\0'
,即
0
,计算结果为false,终止
for
循环。

可以这样重写

for (p = str; *p != '\0'; p++)
{
    // Code
}

在C语言中,字符串必须始终以空字符结尾,这与“\0”或
0
相同,如果两个
之间有任何内容,则for循环将终止为零(false)
*p
取消对p的引用并返回
char
p
指向。根据“C将字符串视为字符数组,通常以标记终止”。该标记是(ASCII)值为零的空字符。所以,这个for循环:

for (p = str; *p; p++)
相当于这些

for (p = str; *p != '\0'; p++)
for (p = str; *p != 0; p++)
for (p = str; p[0] != '\0'; p++)
空终止字符的另一个名称是sentinel或根据Donald Knuth的“虚拟值”(计算机编程艺术,第1卷)。以下是
str
字符串、每个字符的索引(从开始的偏移量)以及每个索引处的值的图表:

为完整起见,在请求注释后,调试器在
str
占用的内存块中看到了以下内容:

0x00007fffffffe6a0:
  0x53 0x6f 0x6d 0x65 0x20 0x54 0x65 0x78 0x74 0x00 0x00 0x00 0x00 0x00 0x00 0x00
     S    o    m    e         T    e    x    t
  • 第一行的十六进制值是该内存块的地址(64位)。这就是
    p
    指向for循环开始处的位置
  • 在第二行,您可以看到字符串中字母的十六进制值。您可以看到一个ASCII表。字符串中的最后一个字符是
    t
    ,十六进制值为
    0x74
    。在此之后,您将获得字符串的空字符
    0x00
    。然后您会看到更多的空字符,因为我是在调试模式下构建的,编译器零初始化。通常您会看到垃圾(看似随机的值)
  • 在第三行,我添加了字符串的字符以供参考
  • 我知道你现在正处在C语言指针的学习过程中,但最终你将能够说“I C the point”

    如图所示,
    for
    循环以
    *p
    开头,其中
    p
    指向
    str
    。此时,
    *p
    具有
    S

    当连续循环
    for
    时,它最终到达
    str[9]
    ,它有
    '\0'
    ,意思是
    NULL

    此时,for(p=str;*p;p++)
    中的条件语句
    *p
    等于
    NULL
    ,因此代码将从
    for
    循环中中断。

    让我们以干燥但深入的方式分析它吧! 或者就像D.里奇所说的:让我们一起做吧


    我将通过参考ISO/IEC:9899(emphasis mine)-C99标准来解释所有必要的方面。 (这篇文章的风格源于唐纳德·克努特(Donald Knuth)的一句话:“科学是我们能够很好地向计算机解释的东西。艺术是我们所做的一切。”)

    首先,让我们检查一下-循环的
    到底应该做什么!
    参考ISO/IEC:9899 6.8.5“迭代声明”

    语义学

    4迭代语句导致称为循环体的语句反复执行,直到控制表达式比较为0

    到目前为止,我想没有什么新鲜事,让我们开始吧:

    6.8.5.3报表格式

    1声明
    for(第1条;表达式-2;表达式-3)语句

    行为如下:表达式expression-2是控制表达式,在循环体的每次执行之前对其进行评估

    因此,我们现在知道,只要您的
    *p
    的预先评估值不为零,主体(在您的示例中为
    //code
    )将被执行

    。。。表达式表达式-3在循环体每次执行后作为无效表达式进行计算。[…]

    所以现在我们知道,(我假设挖掘
    p++
    的定义是没有必要的?!)对于每个迭代
    p
    增量,因此
    *p
    可能会有变化

    下面这一点是不相关的,但我添加它是因为这使得
    for
    的语义部分完整,而且很清楚,因为这就是原因,为什么
    for(;;)
    是一个inf循环

    2(---)第1条和表达式-3均可省略。省略的表达式-2替换为非零常量

    好的,这就是
    for
    循环在您的案例中所做的枯燥但信息丰富的部分

    现在让我们来讨论指针算法: 6.5.6加法运算符

    约束条件

    2对于加法,两个操作数都应为算术类型,或者一个操作数应为指向对象的指针,另一个操作数应为整数类型。(递增等于加1。

    因此,在您的例子中,您将向“指向对象的指针”类型添加1(整数)

    什么是等价物
    0x00007fffffffe6a0:
      0x53 0x6f 0x6d 0x65 0x20 0x54 0x65 0x78 0x74 0x00 0x00 0x00 0x00 0x00 0x00 0x00
         S    o    m    e         T    e    x    t
    
    for (p = str; *p; p++)
    
    p = &str[0];
    p = str; 
    
    char str[128] = "Some Text";
    
    #include <stdio.h>
    int main() {
        char str[128] = "We all scream for ice cream!";
        char *p = str;
        // here we see again the loop exit condition *p == '\0'
        while(*p) {
            printf("%c", *p);
            p++;
        }
        printf("\n");
    }
    
    for( initialization ; Conditional Expression ; expression3)
    {
        Code here will execute while 2nd Expression(Conditional Expression) is true
        true means non-zero value
        '\0' is equivelant to 0,so when *p equal '\0' : loop will terminate
    }
    
        int var=0;
        int *p;
        int p=&var;
    
            int array[3]={9,8,7};
            printf("%d",array[0]); //prints what is on 1st position,9
            printf("%d",array[1]); //prints what is on 2nd position,8
            printf("%d",array[2]); //prints what is on 3rd position,7
    
            printf("%d",*(array+0)); //prints what is on 1st position,9 
            printf("%d",*(array+1)); //prints what is on 2nd position,8
            printf("%d",*(array+2)); //prints what is on 3rd position,7
    
        char str[128] = "Some Text";
        char *p;
    
        for (p = str; *p; p++)
        {
            printf("%c",*p);
        }
    
    if(expr)
    
    if((expr) != 0)  
    
    WHY   for (p=str; *p;        p++)
    IS    for (p=str; p[0] != 0; p++)
    THINK for (i=0;   str[i];    ++i)