你能解释下面的代码,
int main() {
int value = 2;
int *ptrWithAmpersand = &value;
int *ptrWithoutAmpersand = value;
//printf("%d", *ptrWithoutAmpersand); 1) Why Runtime error.
printf("Pointer with & --> %d\n", *ptrWithAmpersand);
printf("Pointer withOUT & and * --> %d\n", ptrWithoutAmpersand); //2) Why this works??!!
getch();
}
如代码中所述
输出
Pointer with & --> 2
Pointer withOUT & and * --> 2
答案 0 :(得分:1)
在:
int *ptrWithAmpersand = &value;
printf("Pointer with & --> %d\n", *ptrWithAmpersand);
您正确地为指针分配地址,并在printf
中正确取消引用它以使用%d
参数打印int。
在:
int *ptrWithoutAmpersand = value;
printf("Pointer withOUT & and * --> %d\n", ptrWithoutAmpersand);
您无意中为指针指定了一个整数值,但由于在printf
中您没有取消引用它,因此它将打印为带有int
参数的%d
。如果sizeof(int *) != sizeof(int)
,这只会导致问题(UB)。
在:
int *ptrWithoutAmpersand = value;
printf("%d", *ptrWithoutAmpersand);
你得到一个运行时错误,因为你要取消引用一个指向内存地址2
的指针,这不是你的,所以系统会中止你的程序。
答案 1 :(得分:1)
在第
行int *ptrWithAmpersand = &value;
您正在创建指向int
的指针,并为其分配变量value
的地址。到目前为止一切都很好。
在第
行int *ptrWithoutAmpersand = value;
您正在创建指向int
的指针,并为其分配变量value
(2)的内容。这导致了几个问题:
您正在尝试将类型int
的值分配给类型为int *
的变量,这些变量不是兼容类型;编译器至少应发出“赋值不兼容类型”或类似内容的警告(打开所有警告)
在您的系统上,2
不是有效的对象地址,因此当您尝试取消引用 ptrWithoutAmpersand
时会出现运行时错误。
您的代码中还有其他几个问题。您不应该使用%d
转换说明符来打印指针值;为此目的始终使用%p
。
这是对代码的轻微改写,使某些事情变得更加清晰:
#include <stdio.h>
int main() {
int value = 2;
int *ptrWithAmpersand = &value;
int *ptrWithoutAmpersand = value; // throws a warning in gcc; you should not do this
printf("value of expression \"value\" = %d\n", value );
printf("value of expression \"&value\" = %p\n", (void *) &value );
printf("value of expression \"ptrWithAmpersand\" = %p\n", (void *) ptrWithAmpersand );
printf("value of expression \"*ptrWithAmpersand\" = %d\n", *ptrWithAmpersand );
printf("value of expression \"ptrWithoutAmpersand\" = %p\n", (void *) ptrWithoutAmpersand );
return 0;
}
以下是代码的输出:
value of expression "value" = 2
value of expression "&value" = 0x7ffecb63cf44
value of expression "ptrWithAmpersand" = 0x7ffecb63cf44
value of expression "*ptrWithAmpersand" = 2
value of expression "ptrWithoutAmpersand" = 0x2
注意如何打印指针表达式与整数表达式。
简而言之:
*ptrWithAmpersand == value == 2 type == int
ptrWithAmpersand == &value type == int *
ptrWithoutAmpersand == value == 2 mismatched types int * and int