const限定符一般用来说明不变量,也就是常量。这个本身很简单,没啥技术含量,但是const跟指针搅和到一块去就不好玩了,事情就会变得复杂了。下面我们来分析一下const的用法
针对普通变量的场景:
const int val = 1024; // correct
const int val1 = val; // correct
const int val2; //wrong, const value must be initialized
const int val1 = 1111; // wrong, val1 is a const value
当我们定义了const类型的变量后,必须将其初始化,使其变为一个常亮,同时再也不能给这个量赋值了,因为他是一个常量。
针对引用的场景:
const int val = 1024;
const int &rel = val; // correct
int &rel1 = val // wrong, val is a const value, must use const reference
rel = 42; // wrong,
int val1 = 2048;
const int &rel2 = val1; // correct
const int &rel3 = 42; // correct
int &rel4 = rel2; // wrong
针对引用,const引用可以对const常量或者赋值的变量使用,但是不能修改引用。同时非const的引用不能引用const的引用
针对指针的场景:
这个就是最复杂的场景了,const加上指针直接会让人崩溃的。
const int ptr; // 这是一个指向const int常量的指针,它指向的值不能修改,但是指针本身可以修改
int const ptr; // 指向int类型的const指针,它不能指向别的变量,但是它指向的变量的值是可以改动的
int const ptr; // 这个和上面的是一样的
const int const ptr; // 正常整形常量的常量指针, 它不能指向别的变量,它指向的变量的值也不能修改
抓住一点本质,const跟谁近,就表示谁是const的。
const int val = 1024;
int ptr = &val; // wrong, must use const int ptr
const int *ptr1 = &val; // correct
int val = 1024;
int *const ptr = &val; // ptr将会一直指向val,但是val的值是可以变得。
const int val = 1024;
const int *ptr = &val; // ptr可以指向其他的值,但是它指向的值不能变
代码样例:
int main() {
int val = 1024;
int const ptr = &val;
std::cout << ptr << std::endl;
val = 2048;
std::cout << *ptr << std::endl;
const int val1 = 1024;
const int* ptr1 = &val1;
std::cout << *ptr1 << std::endl;
int val2 = 3072;
ptr1 = &val2;
std::cout << *ptr1 << std::endl;
return 1;
}
1024
2048
1024
3072
如果是下面的这样,就会报错:
int main() {
int val = 1024;
int const ptr = &val;
std::cout << ptr << std::endl;
int val1 = 2038;
ptr = &val1; // wrong, ptr指针是const的,不能指向别人
std::cout << *ptr << std::endl;
return 1;
}
针对函数的。
在函数中我们也可以用const来进行修饰。如果在函数前,则表示返回值是const的,在函数名后呢,则表示函数不能修改类的成员。1
2
3const int Screen::some_member() {
return access_ptr;
}
1 | int Screen::some_member() const { |
注意const位于函数名后面的场景是有限定条件的:
非静态成员函数后面加const(加到非成员函数或静态成员后面会产生编译错误)
如果一定要修改,则可以将成员变量定义为mutable类型的,这个在类里面会介绍。