C中的指针到const转换
以下代码在GCC上编译时没有警告,但在Visual Studio 2005中发出警告。
const void * x = 0; char * const * p = x;
x指向未知类型的常量对象,p指向char的常量指针。 为什么p的赋值会导致警告?
同样,这是C,而不是C ++。 谢谢。
它发生的原因是当你将一种类型的指针指向另一种类型时, 有时会无意中完成 (bug),因此编译器会向你发出警告。
因此,为了告诉编译器您确实打算这样做,您必须进行显式转换,如下所示:
const void * x = 0; char * const * p = (char * const * )x;
PS在我写的第一个地方“ 大部分时间都是无意中完成的”,但当他理所当然地说无效*专门用于此目的时,AndreyT让我重新考虑它。
C代码是有效的,并且一致的编译器不应该警告,因为const
ness被正确保留,并且void *
转换为任何指针类型(旁边的函数指针)都是隐式的。
C ++编译器应该警告隐式转换,但是关于丢弃const
限定符的警告是错误的,应该被视为编译器错误。
如果x
指向一个struct Thing
而不是一个char
,该怎么办? 在这种情况下,您将使用未指定的行为做某事。 海湾合作委员会倾向于让你这样做,因为它假设你足够聪明,不会在脚下射击自己,但有充分的理由发出警告。
您必须从右到左阅读以下内容。
char * const * p = x;
例如:
P指向char类型的const指针。
const void * x = 0; char * const * p = x;
起初我假设你打算取x的地址并为此编写代码。 然后我决定x指向char []的指针。 无论如何,它仍然令人困惑:
#include int main() { char s [] = "Hello World!"; const void * x = s; const char * const * const p = (const char * const *)&x; printf("%s\n", *p); /* won't compile *p++; // increments x to point to 'e' (**p)++; // increments 'H' to 'I' */ const char * y = s; x = &y; const char * const * const q = x; printf("%s\n", *q); /* won't compile *q++; (**q)++; */ return 0; }
p
声明中char
之前的额外const
阻止(**p)++
编译。 但是,在声明q
(在GCC中)阴影warning: dereferencing 'void *' pointer
之前添加的const
warning: dereferencing 'void *' pointer
有error: increment of read-only location '**q'
对于(**q)++
error: increment of read-only location '**q'
。 希望有所帮助,它对我有所帮助:-)
warning C4090: 'initializing' : different 'const' qualifiers
您不能将const void
为char *const
甚至char *
。 通过解除引用p
,您现在可以修改*(char *)(*x)
。 关于C中的指针,这是一个鲜为人知的微妙之处。
p
的工作类型是:
char const **p = x;
是的,我像男人一样把const
放在右边。