用法指针算术混淆

时间:2015-11-26 16:07:28

标签: c pointers

我对使用指针算法有点困惑。我在代码中提出令人困惑的问题作为评论。我认为当它增加时,另一个也必须增加。有人可以解释一下吗?

#include <stdio.h>

int main()
{
    const char *str = "abcde";

    const char *temp = str; // str is pointer to address of first element of temp isn't it?

    printf("%d\n", temp - str); // zero okey

    printf("temp   str\n");

    printf("%d   %d\n", temp, str); // shows same adresses

    str++;  // hard to understand a point is here

    printf("%d   %d\n", temp, str); // why weren't also temp increased?

    temp++;

    printf("%d   %d\n", temp, str); // why weren't also str increased?

    temp++;

    printf("%d   %d\n", temp, str); // why weren't also str increased?

    return 0;
}

5 个答案:

答案 0 :(得分:1)

tempstr都是不同的指针变量。修改其中任何一个都不会导致其他修改,但修改他们指向的数据将会生效。

您应该记住,在您的情况下,您可以修改strtemp但不能修改它们指向的字符串文字,因为字符串文字不可修改。

另请注意,对于指针数据,%p用作printf中的格式说明符,以打印它们指向的地址。

答案 1 :(得分:0)

temp不会因增加str而增加,因为ba增加int a=0, b=0;而无法增加str。它们是自变量。

"abcde"是指向temp的第一个元素的地址的指针,它不会与temp建立任何关系,因为它是在定义%d之前定义的。

顺便说一句,不要尝试使用#include <stdio.h> int main(void) { const char *str = "abcde"; const char *temp = str; // str is pointer to address of first element of temp isn't it? printf("%ld\n", (long)(temp - str)); // zero okey printf("temp str\n"); printf("%p %p\n", (void*)temp, (void*)str); // shows same adresses str++; // hard to understand a point is here printf("%p %p\n", (void*)temp, (void*)str); // why weren't also temp increased? temp++; printf("%p %p\n", (void*)temp, (void*)str); // why weren't also str increased? temp++; printf("%p %p\n", (void*)temp, (void*)str); // why weren't also str increased? return 0; } 打印指针。这是未定义的行为,因为类型不匹配。

 public function scopeGetCategorieSlug($query, $category_slug)
{
    return $query->leftJoin('category_product', 'category_product.product_id', '=', 'products.id')
                ->leftJoin('product_categories', 'product_categories.id', '=', 'category_product.category_id')
                ->where('product_categories.slug', $category_slug)
                ->get(['products.*']);
}

答案 2 :(得分:0)

在您的代码中,tempstr 自己两个不同的变量,但是,它们指向的数据是相同的。< / p>

如果您修改其中任何一个指向的内容,您可以看到通过其他内容反映的更改。

另外,FWIW,用于打印地址,更改

 printf("%d   %d\n", temp, str);

 printf("%p   %p\n", (void *) temp, (void *)str);

否则,通过违反格式说明符的适当类型参数的要求,您将调用undefined behavior

答案 3 :(得分:0)

const char * temp = str; 表示临时指针获取str指针的值。 他们没有联系。 你可以改变str而不改变temp,因为它就像 * temp =&amp;(str [0]); * temp值是字符串“abcde”中'a'的地址 如果你是str ++ * temp值是字符串“abcde”中'a'的地址,* str是'b' 我不知道我为你做了什么。

答案 4 :(得分:0)

此声明

const char *str = "abcde";

表示以下内容。为变量str分配了内存,它由字符串文字"abcde"的第一个字符的地址初始化

在此声明中

const char *temp = str;

为另一个名为temp的指针分配内存,指针获取存储在变量str中的值的副本

所以现在你有两个内存单元格,每个单元格都包含字符串文字的第一个字符的地址。

本声明

str++;  // hard to understand a point is here

表示存储在str中的值增加了。前一个值是字符串文字的第一个字符的地址。现在增加值后,它等于字符串文字的第二个字符的地址。

您可以通过在此语句之前和之后执行调用函数printf的语句来检查这一点

printf( "%s\n", str );

str++;  // hard to understand a point is here
printf( "%s\n", str );

存储在变量temp中的值未更改。

在此声明之后

temp++;

两个变量具有相等的值,这些值是指向字符串文字的第二个字符的指针。存储在名为strtemp的不同内存单元格中的值。

在第二个陈述之后

temp++;

变量temp的值等于字符串文字的第三个字符的地址。存储在变量str中的值未更改。

您应该知道字符串文字包含终止零。您可以输出字符串文字的所有字符,直到遇到终止零。

请考虑以下代码段

const char *str = "abcde";
const char *temp = str;

while ( *temp != '\0' ) printf( "%s\n", temp++ );

循环变量temp之后将具有指向字符串文字的终止零的值。同时,存储在str中的值不会被更改,并且将像以前一样指向字符串文字的第一个字符。