为什么下面给出了从double***到const double***的转换错误

veh*_*zzz 2 c

为什么不能转换double ***const double ***

void foo(const double ***d)
{


}


int main (int args, char*[] args)
{
       double ***d;
       /*initialize d */

       foo(d);

}
Run Code Online (Sandbox Code Playgroud)

Pet*_*ham 8

如果你的C标签是可信的,gcc会生成一个警告,因为你的例子和类型都有不同的类型const double * const * const * d.在C++中,它是OP代码中的错误,但slap-const-everywhere方法是合法的.

编译器警告您的原因是指向指针(或进一步间接)的指针允许通过修改参数指向的位置将指针返回给调用者.

如果指针的目标被声明为const,那么被调用的函数将期望它放在那里的值在返回时被视为const.

传递T**给a的一个更简单的例子const T**说明了为什么这是一个错误将是:

void foo ( const char ** z )
{
    *z = "A";
}


int main (int nargs, char** argv)
{
    char*   z = 0;
    char**  d = &z;

    // warning in C, error in C++
    foo ( d );

    // bad - modifies const data
    z[0] = 'Q';
}
Run Code Online (Sandbox Code Playgroud)

const在C中意味着数据不会改变.const在C++中意味着数据不会公开更改 - C++对象中的可变数据可能会发生变化.AC编译器可以优化其代码,以便在const某处缓存某些数据,但由于可能的可变性,C++编译器无法做到这一点,因此有一个较弱的限制,即您无法将const数据返回到非const,如上所述.所以在C++中,double***可以转换const double * const * const * d为额外的consts来防止返回不可修改的内存,但是在C中,如果编译器优化了对其他地方的内存的重复访问,它会生成警告和可能的错误.