primer第四版是上面的说法,但我在VS2012中,const也可以指向一个本类型的非const变量,查找资料的原因大概是满足reference-campatible条件。
理论上,我们应该严格遵守,常量引用指向常量对象,非常量引用指向非常量对象,避免出错。
3. const与指针
const与指针的关系分为两种:const修饰的指针和指向const对象的指针,二者const的位置不相同
3.1 指向const对象的指针(const位于指针符号*前面)
对于一个const对象,必须用一个指向const的指针来指向它。原因在于,const修饰使得对象无法被改变,而指针如果不是指向const的指针,则可以通过指针来修改对象,这是不被允许的。
const int ival = 1;
const int *ptrVal = &ival;
反过来,对于一个指向const对象的指针,可以指向任意一个对象,这个该怎么理解呢?我们首先看看指针赋值的过程:
int *ptr = &val;
将val的地址赋值给ptr,因为赋值的只是地址,所以不知道ptr所指向的对象是否为const。
如果我们把一个地址赋值给一个指向const的指针,那么指针认为这是一个const的对象,也就是说,ptr指针指向了一个“自认为”是const的对象。
int ival = 1;
const int *ptrVal = &ival;
上面的程序是正确的,我们需要明确,ival是非const变量,所以我们可以通过给ival赋值更改ival的值。ptrVal指向了一个自认为是const的对象,所以我们无法通过*ptrVal来更改ival的值。
3.2 const修饰的指针(const位于指针符号*后面)
int *const ptr;
上式声明了一个const类型的指针,表示的意思是指针本身是一个常量,不能被修改。
如何理解?指针本身的值是一个地址,如果指针本身是一个常量,则这个地址值不能被修改,也就是说指针只能指向这个地址,不能指向其他地方。但指针所指向的地址的内容不属于指针本身的值,所以其所指向的内容可以改变。
int ival = 1;
int *const ptr = &ival;
*ptr = 2; // ok
int ivalTwo = 11;
ptr = &ivalTwo // error
综上,可以定义一个指向const对象的const指针










