C字符串指针。整数指针与字符指针

时间:2020-08-13 04:56:00

标签: c pointers c-strings

我想知道为什么* 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 
    }

2 个答案:

答案 0 :(得分:5)

为什么'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组成,因此您的{ {1}}是完全可以预期的。

jucem n 1 ??

您声明'k' 指针类型控制指针算术 。因此,int *p使p++前进p个字节(通常为4个字节),而不是sizeof(int)个字节(1个字节)。因此,让我们看一下:

sizeof(char)

每增加4个字节,您就有 john q public ------------- 0123456789012 ^ ^ ^ ^ 4-bytes per p++ | p ,其中j uc...表示您通过访问...数组末尾的内存来调用未定义行为的位置-所有的赌注都没有。

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

始终在启用了警告的情况下进行编译,并且在未经警告的编译之前,不接受的代码。要启用警告,请在您的name编译字符串中添加-Wall -Wextra -pedantic(也可以考虑添加gcc/clang来警告阴影变量)。对于 VS (在Windows上为-Wshadow),请使用cl.exe。所有其他编译器将具有类似的选项。阅读并理解每个警告-然后修复它。他们将确定任何问题以及发生问题的确切路线。通过听编译器告诉您的内容,您可以学到很多东西。

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

/W3

答案 1 :(得分:3)

一些可能有用的东西:

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开始)

相关问题