简体   繁体   English

C中的双指针const正确性警告

[英]Double pointer const-correctness warnings in C

A pointer to non-const data can be implicitly converted to a pointer to const data of the same type: 指向非常量数据的指针可以隐式转换为指向相同类型的常量数据的指针:

int       *x = NULL;
int const *y = x;

Adding additional const qualifiers to match the additional indirection should logically work the same way: 从逻辑上讲,添加其他const限定符以匹配其他间接寻址应以相同的方式进行:

int       *      *x = NULL;
int       *const *y = x; /* okay */
int const *const *z = y; /* warning */

Compiling this with GCC or Clang with the -Wall flag, however, results in the following warning: 但是,使用带有-Wall标志的GCC或Clang进行编译会导致以下警告:

test.c:4:23: warning: initializing 'int const *const *' with an expression of type
      'int *const *' discards qualifiers in nested pointer types
    int const *const *z = y; /* warning */
                      ^   ~

Why does adding an additional const qualifier "discard qualifiers in nested pointer types"? 为什么要添加额外的const限定词“在嵌套指针类型中丢弃限定词”?

The reason why const can only be added one level deep is subtle, and is explained by Question 11.10 in the comp.lang.c FAQ . const只能被const添加的原因是微妙的,由comp.lang.c FAQ中的问题11.10进行了解释。

Briefly, consider this example closely related to yours: 简要地,请考虑与您的示例紧密相关的示例:

const int i;
int *p;
int const **z = &p;
*z = &i;
/* Now p points to i */

C avoids this problem by only allowing assignment to discard qualifiers at the first pointed-to level (so the assignment to z here is not allowed). C通过仅允许分配在第一个指向级别上丢弃限定符来避免此问题(因此,此处不允许分配给z )。

Your exact example does not suffer from this problem, because the const the second level means that the assignment to *z would not be allowed anyway. 您的确切示例不会遇到此问题,因为const第二级意味着无论如何都不允许分配给*z C++ would allow it in this exact case, but C's simpler rules do not distinguish between your case and the example above. C ++ 允许它在这个确切情况,但是C的简单规则,不会将您的情况和上面的例子加以区分。

The FAQ entry linked by the other answer explains why the following code is not permitted: 由其他答案链接的FAQ条目解释了为什么不允许以下代码:

int **x = whatever;
const int **z = x;

However, your code const int *const *z = x; 但是,您的代码const int *const *z = x; is quite different, and it does not suffer from the same flaw raised by the FAQ. 完全不同,并且不会遇到FAQ提出的相同缺陷。

In fact, there is conceptually nothing wrong with the latter code. 实际上,后一种代码在概念上没有错。 It is just a flaw in the C specification that it is not permitted, and it forces C programmers to include ugly casts in their code. 不允许这样做只是C规范中的一个缺陷,它迫使C程序员在其代码中包含丑陋的强制类型转换。

It would have been possible for C to use the same rules that C++ did; C可能会使用与C ++相同的规则。 however the C standard committee didn't decide to do that. 但是C标准委员会没有决定这样做。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM