在最后两个陈述中,realPointer
和fakePointer
之间存在任何真正的差异。他们都会提供相同的功能吗?
int num = 0;
int *realPointer = #
int fakePointer = #
int fakePointer = #
这不是有效的C,它打破了简单赋值的规则而不会编译。
但是,如果你完成了int fakePointer = (int)#
,那么唯一的区别就是无法保证你可以可靠地使用fakePointer,从指针到整数的转换是实现定义的,并且可能还会导致未定义的行为(6.3.2.3):
任何指针类型都可以转换为整数类型。除了之前指定的以外,结果是实现定义的。如果结果无法以整数类型表示,则行为未定义。结果不必在任何整数类型的值范围内。
要在指针和整数之间进行安全且可移植的转换,不应使用int
,而应使用stdint.h中的uintptr_t
类型。
声明为指针的变量在语义上与未声明为指针的变量不同。编译器(和语言)将允许您使用非指针无法执行的指针执行操作。当然,情况正好相反。
最大的不同是你可以取消引用一个指针,但你不能这样做非指针。
例如,使用代码中的变量,然后我们可以执行*realPointer = 5
以使num
被赋值为5
,但是不允许执行*fakePointer = 5
并且没有意义,因为fakePointer
实际上不是指针。
int num = 0;
int *realPointer = #
int fakePointer = #
在最后两个语句中,realPointer和fakePointer之间存在任何真正的区别。
你的fakePointer
不是指针。它是一个整数,其值为变量num的地址。使用默认选项编译时,您可能会离开。但正如Lundin指出的那样,这确实是一个无效的代码。使用gcc
和CFLAGS="-g -Wall -std=c99 -O3 -pedantic-errors"
标志,你会收到这个错误:
error: initialization makes integer from pointer without a cast
虽然你的realPointer
确实指向变量num
,你可以取消引用它。你可以用你的fakePointer
做任何事情 - 事实上,fakePointer
本身的任务无效。
如果你考虑这两个变量所保持的文字值(即实际值),它们是相同的(即变量num的地址),但只有值相同。但正如其他人所说,它们在语义上是两个不同的变量,不能互换使用。
来到你的上一个问题:
Will they both provide the same functionality? Answer: No, they do not. Reasoning they are not of the same type. Your first question: any real difference between the realPointer and fakePointer. There are so many differences, and the most basic differences are:除此之外
int fakePointer = #
可能导致以下一种或多种情况
以下差异适用:
*
- / dereferencing-operator不能应用于int
类型的fakePointer
。fakePointer++
很可能会产生与realPointer++
不同的东西。这适用于添加和减去任何值的所有其他方式(但0
)。请阅读"pointer arithmetic"与“算术”的详细信息。[]
- / indexing-operator应用于int
类型的fakePointer
。