在 C + + 中将 const 转换为 Non-const

这些天我真的很烦 const关键字,因为我不是很熟悉它。我有一个向量,它存储所有常量指针,比如 vector<const BoxT<T> *> *Q_exclude,在另一个类的构造函数中,我需要这个队列中的一个元素作为参数传入,并将它分配给一个非常量成员。我的问题是:

如何将常量变量赋给非常量变量?我知道这是没有意义的,因为毕竟,一个 const 是一个 const,不应该被任何方式改变。但是,这个恼人的成员变量真的必须在这个过程中改变!我还可以将向量中的数据类型更改为 non-const,但这样做的工作量太大。或者有人知道如何避免这种情况吗?

160991 次浏览

更改常量类型将导致 未定义行为

但是,如果您有一个原始的非 const 对象,该对象由指针指向 const 或由引用 const 引用,那么您可以使用 Const _ cast来消除该 const。

抛弃常态被认为是邪恶的,应该避免 。如果要通过向量修改数据,应该考虑将向量中使用的指针的类型更改为 non-const。

抛弃指针常量的实际代码是:

BoxT<T> * nonConstObj = const_cast<BoxT<T> *>(constObj);

但请注意,这确实是作弊。一个更好的解决方案要么是弄清楚为什么要修改 const 对象,然后重新设计代码,这样就不必... ..。或者从向量中移除 const 声明,如果结果是你并不真的希望这些条目是只读的。

您可以将一个 const对象分配给一个非 const对象。因为您是 收到,因此创建了一个新对象,所以不违反 constness。

像这样:

int main() {
const int a = 3;
int b = a;
}

如果你想获得一个指针或者引用原来的 const对象,那么 是不同的:

int main() {
const int a = 3;
int& b = a;       // or int* b = &a;
}


//  error: invalid initialization of reference of type 'int&' from
//         expression of type 'const int'

如果必须的话,您可以使用 const_cast来修改类型安全,但是请记住,您正在做的正是这件事: 去掉类型安全。在 下面的例子中通过 b修改 a是未定义的 还是:

int main() {
const int a = 3;
int& b = const_cast<int&>(a);


b = 3;
}

虽然它编译没有错误,任何事情都可能发生,包括打开一个黑洞或转移到我的银行帐户你辛苦赚来的储蓄。

如果您已经达到了您认为需要这样做的要求,那么我将迫切地重新审视您的设计,因为它存在某些非常错误的地方。

void SomeClass::changeASettingAndCallAFunction() const {
someSetting = 0; //Can't do this
someFunctionThatUsesTheSetting();
}

另一种解决方案是在对 const 函数使用的变量进行编辑之间调用上述函数。这个想法解决了我的问题,因为我不愿意更改函数的签名,而必须使用“ changeASettingAndCallAfunction”方法作为中介:

当你调用这个函数的时候,你可以在调用之前先对设置进行编辑,或者(如果你不想扰乱调用的位置)也可以调用这个函数,在这里你需要对变量进行修改来进行传播(就像我的例子)。

void SomeClass::someFunctionThatUsesTheSetting() const {
//We really don't want to touch this functions implementation
ClassUsesSetting* classUsesSetting = ClassUsesSetting::PropagateAcrossClass(someSetting);
/*
Do important stuff
*/
}


void SomeClass::changeASettingAndCallAFunction() const {
someFunctionThatUsesTheSetting();
/*
Have to do this
*/
}


void SomeClass::nonConstInvoker(){
someSetting = 0;
changeASettingAndCallAFunction();
}

现在,当调用一些对“ somFunctionThatUseTheSeting”的引用时,它将通过对 somSetting 的更改来调用。

把这个留给我自己,

如果我得到这个错误,我可能使用 const char*时,我应该使用 char* const

这使得指针成为常量,而不是字符串的内容。

const char* const使它的值和指针也是常数。