在阅读用C ++编写的教程和代码时,我经常偶然发现const
关键字。
我看到它的用法如下:
const int x = 5;
我知道这意味着x
是一个常量变量,可能存储在只读内存中。
但是
void myfunc( const char x );
和
int myfunc( ) const;
答案 0 :(得分:49)
void myfunc(const char x);
这意味着参数x
是一个char,其值在函数内部无法更改。例如:
void myfunc(const char x)
{
char y = x; // OK
x = y; // failure - x is `const`
}
对于最后一个:
int myfunc() const;
这是非法的,除非它在类声明中 - const
成员函数阻止修改任何类成员 - const
非成员函数不能使用。在这种情况下,定义将类似于:
int myclass::myfunc() const
{
// do stuff that leaves members unchanged
}
如果您需要在const
成员函数中修改特定的类成员,则可以声明它们mutable
。一个示例是成员lock_guard
,它使类const
和非 - const
成员函数线程安全,但必须在其内部操作期间发生更改。
答案 1 :(得分:9)
第一个功能示例或多或少没有意义。更有趣的是:
void myfunc( const char *x );
这告诉编译器不会修改*x
的内容。也就是说,在myfunc()
范围内,您无法执行以下操作:
strcpy(x, "foo");
第二个例子,关于C ++成员函数,意味着调用不会改变对象的内容。
所以给出:
class {
int x;
void myfunc() const;
}
someobj.myfunc()
不允许修改以下内容:
x = 3;
答案 2 :(得分:2)
此:
void myfunc( const char x );
表示你无法在函数内部更改x
,即这是非法的:
void myfunc( const char x ) {
x = ...;
}
,同时:
int myfunc() const;
只有myfunc()是类中的方法才有意义;它基本上意味着该方法不能修改类实例(即调用instance.myfunc()之前和之后实例的状态将是相同的。)
答案 3 :(得分:2)
在变量标识符之前,const
表示该变量可以初始化,之后不会被修改。
在类方法名称之后,const
表示该方法不会修改类的可观察状态。 mutable
关键字允许修改内部数据。
在指针或引用变量之前,const
表示该标识符不会用于修改引用的数据,但可以通过其他方式更改。
const int *pInt = &x;
Const也可用于指示无法修改指针本身:
int * const pInt = &x;
答案 4 :(得分:1)
我在http://duramecho.com/ComputerInformation/WhyHowCppConst.html
找到了一个非常好的解释基本上所有的混淆都在于关键字const
的不同用例。根据您放置const
的位置,您可以告诉某些内容应该是不可变的,或者某些东西不能更改其他内容。 'something'可能是变量或指针或函数/方法,您不希望它能够更改传递给对象的函数或成员变量的变量值。
答案 5 :(得分:0)
两者之间的区别在于第一个类型为void(char)
,第二个类型为int()const
。
在末尾具有const
类型的函数只能是类的成员函数,这意味着成员函数不会更改类值(this
指的是从课外看到的。编译器会检查到某种程度,并且对const成员函数中的类成员的任何直接写入都会导致编译时错误,并且该函数可以直接调用自身的const成员函数(存在特殊指令,因此您可以告诉成员编写的编译器不会改变从外部看到的类的值。这由mutable
关键字完成。
在您提供的功能中,其中一个参数的类型为char const
。这样的参数不能在其功能内改变。它虽然对函数的类型没有影响,但对函数的调用者没有影响。
答案 6 :(得分:0)
void myfunc(const char x)
与示例中的const int x = 5
非常相似:它在函数myfunc
中声明了一个本地可用的常量。因为它是一个常数,所以它的价值无法改变。
int myfunc() const
是类的成员函数。 const
表示该函数不会更改执行该函数的类的实例。因此,在函数中,您不能执行this->foo = 7
之类的操作或调用非常量的其他函数。
答案 7 :(得分:0)
const
限定符意味着您的程序可能不会更改定义为const
的变量/指针,它将通过显式初始化或依赖于硬件的方式接收其值。 / p>
在参数声明中定义为const
的指针,功能代码不会修改它指向的内容。基本上,您可以使用指针,它几乎可以作为“只读”。
例如: -
void foo(const char *x)
{
while(*x)
{
if(*x==' ') cout << '-'; //printing - when a space is encountered
else cout << *x;
x++;
}
}
上述功能正常,不会显示任何错误。但是,如果foo有任何可以改变传递的字符串的东西。说一个用$替换空格的函数。不打印$但将其更改为$。这样的事情: -
void foo(const char *x)
{
while(*x)
{
if(*x==' ') *x = '$'; //printing - when a space is encountered
else cout << *x;
x++;
}
}
然后它不会编译,即分配错误到只读存储器位置。
答案 8 :(得分:0)
接受的答案(以及我略读的其他答案)不正确。 不要假设“const”意味着一个标识符(比如你的 x)“不能在函数内部改变”。这意味着不能直接更改标识符。但它很容易改变。
考虑完整的程序(为新手编写):
#include <iostream>
void break_const(const int x) {
const int* x_ptr = &x;
std::intptr_t z = reinterpret_cast<std::intptr_t>(x_ptr);
int* hacked = reinterpret_cast<int*>(z);
*hacked = 3;
std::cout << "x = " << x << std::endl;
}
int main() {
break_const(5);
return 0;
}
输出是“x = 3。”
编辑:我还应该补充一点,我的陈述“这意味着不能直接更改标识符”有点不对。对于整数,没问题。但是对于更复杂的类型,const 意味着更少(例如,在类中可变)。