C 字符串指针。 int 指针与 char 指针

C string pointer. int pointer vs char pointer

我想知道为什么 *p+1 输出 k 而不是 "o"?我已经尝试 运行 使用调试器进行此操作,但似乎仍然无法解决这个问题。

    char name[] = "john q public";
    int *p = name;
    printf("%c\n", *p+1); // output expected -> o, but got k
    printf("%c", name[0]); // output as expected -> j

当我尝试在 for 循环中输出名称时,我得到了奇怪的值。

    int  len = strlen(name);
    for(int i=0; i<len; i++ ){
        printf("%c", *p++); //expected -> john q public, but got -> j ucem n 1 
    }

一些可能有帮助的事情:

printf("%c\n", *p+1);

这是将 *p 的 ascii 值加 1,所以 'j' + 1 = 'k'(您得到的值)。
你想要的大概是:

printf("%c\n", *(p+1));

此外,您制作了一个 int 指针,但我认为在这种情况下您需要一个 char 指针。

总而言之,这是我建议的用于获取带有指针的字符串的第一个字符的编辑:

char name[] = "john q public";
char *p = name;
printf("%c\n", *(p));

(不需要“+1”,因为数组从 0 开始)

为什么 'k'

您声明:

char name[] = "john q public";

访问时,name 被转换为指向第一个元素的指针(指向 'j' 的指针)C11 Standard - 6.3.2.1 Other Operands - Lvalues, arrays, and function designators(p3)

您分配:

int *p = name;

所以 p 将存储 'j' 的内存位置(地址)作为其值(例如 p 指向 'j')。然后打印 printf("%c\n", *p+1);,其中取消引用 p(例如 *p)是字符 'j' 并通过 ASCII Table and Descriptionj + 1 == k,因此您的输出 'k' 完全符合预期。

j ucem n 1??

你声明int *p指针类型控制指针运算。因此 p++p 提前 sizeof(int) 字节(通常为 4 字节)而不是 sizeof(char) 字节(1 字节)。那么让我们看看:

    john q public
    -------------
    0123456789012
    ^   ^   ^   ^   4-bytes per p++
    |
    p

增加 4 个字节你有 j uc... 其中 ... 表示你在哪里调用 未定义的行为 通过访问超出 [=15 结束的内存=] array -- 所有赌注都关闭了。

始终在启用警告的情况下进行编译

始终在启用警告的情况下编译,并且不要接受代码,直到它在没有警告的情况下编译.要启用警告,请将 -Wall -Wextra -pedantic 添加到您的 gcc/clang 编译字符串(也可以考虑添加 -Wshadow 以警告阴影变量)。对于 VScl.exe on windows),使用 /W3。所有其他编译器都有类似的选项。阅读并理解每个警告——然后去修复它。他们将确定任何问题,以及问题发生的确切路线。通过聆听编译器告诉您的内容,您可以学到很多东西。

如果您在启用警告的情况下进行编译,您会发现:

warning: initialization from incompatible pointer type [-Wincompatible-pointer-types]
 int *p = name;