> 文章列表 > C++ const的作用

C++ const的作用

C++ const的作用

1.const在C中是只读变量,在C++中表示常量
以下代码,在C中是错误的,但是在C++中是正确的。

void main()
{const int n = 10;int arr [n];
}

2.const不仅可以定义一个常量,也可以定义函数参数
例如:

char *strcpy(char *dest,const char*src)
int strcmp(const char*src1,const char*src2)

3.const可以定义指针

void main()
{int a = 10;const int* p1 = &a;int* const p2 = &a;int const *p3 = &a;const int * const p4 = &a;
}

(1)第一个const修饰的是*p1,也就是修饰的是p1所指向的内容,所以*p1不可以自加,*(p1)++;不能执行,p1++;是可以执行的。
(2)第二个const修饰的是p2本身,它所指向的内容是int,*(p2)++;可以执行,p2++;不可以执行的,因为p2本身不可以自加。
(3)第三个const修饰的是*p3,也就是修饰的是p3所指向的内容,所以*p3不可以自加,*(p3)++;不能执行,p3++;是可以执行的。
(4)第四个const修饰的是*p4,第五个const修饰的是p4本身,*(p4)++;不能执行,p4++;也不可以执行。
【说明】把const 和 int 互相颠倒对const修饰什么无影响,const修饰什么是看*,看*放在const之前还是放在const之后。
4.const可以修饰函数返回值
(1)以下代码想要在主函数直接通过a.m_i输出i的值以及修改i的值,但是都不能执行,因为m_i是私有的。

class A
{
public:A(int i = 0){m_i = i;}void print() { cout << m_i << endl; }
private:int m_i;
};
void main()
{A a(30);a.print();//cout << a.m_i << endl;  //错//a.m_i = 50;      //错
}

【运行结果】
C++ const的作用
(2)我们可以给一个接口GetI()函数,用来获取m_i的值,此时就可以通过a.GetI输出m_i的值,但是仍然不能通过a.GetI去修改m_i的值。

class A
{
public:A(int i = 0){m_i = i;}void print() { cout << m_i << endl; }int GetI(){return m_i;}    
private:int m_i;
};
void main()
{A a(30);a.print();cout << a.GetI() << endl;//a.GetI() = 50;   //错
}

【运行结果】
C++ const的作用
不能通过a.GetI()修改m_i的值是因为a.GetI()不能作为左值,因为左边的表达式a.GetI()返回m_i,不是把m_i本身返回,是相当于把m_i的值先给了一个临时变量,再把临时变量的值返回去,然后临时变量的空间也消失掉了,所以a.GetI()没有确定的内存空间,不能作为左值,因为要想作为左值必须要有一个确定的内存空间。
(3)如果我们想通过a.GetI()修改a.m_i的值,可以给int GetI()加一个引用,变成int& GetI(),因为引用是当前实体的别名,相当于把m_i本身返回去,此时a.GetI()可以作为左值,就可以通过a.GetI()来修改a.m_i的值

class A
{
public:A(int i = 0){m_i = i;}void print() { cout << m_i << endl; }int& GetI(){return m_i;}
private:int m_i;
};
void main()
{A a(30);a.print();a.GetI() = 50;cout << a.GetI() << endl;
}

【运行结果】
C++ const的作用
(4)用const修饰函数返回值:const int& GetI(),此时又不能通过a.GetI()来修改a.m_i的值,但是可以通过a.GetI()来输出a.m_i的值也可以把a.GetI()放在右边。

class A
{
public:A(int i = 0){m_i = i;}void print() { cout << m_i << endl; }const int& GetI(){return m_i;}
private:int m_i;
};void main()
{A a(30);a.print();cout << a.GetI() << endl;//a.GetI() = 50;    //错
}

【运行结果】
C++ const的作用
比较以下两部分代码:

    int GetI(){return m_i;}    
   const int& GetI(){return m_i;}

(1)第一部分代码的返回值是临时的m_i,临时变量不能作为左值,所以不能修改m_i的值,第二部分代码返回的时候没有生成临时的变量,返回的值就是m_i本身,但是因为加了const所以不能修改m_i的值。
(2)第二部分代码相比较第一部分代码的好处是,第二部分代码虽然因为加了const不能作为左值,但是它返回的就是m_i本身,而第一部分代码不仅不能作为左值被修改,还生成了临时变量,最终临时变量要消失,空间要释放,开辟空间,释放空间,效率就变慢了。
5.const可以修饰常成员函数,const写在函数参数之后

class A
{
public:A(int i = 0){m_i = i;}void print() { cout << m_i << endl; }void print()const { cout << "const" << m_i << endl; }//上面两个函数构成重载,函数后面加const可以构成重载const int& GetI()const   //常成员函数,在当前函数中不能修改本类数据成员的值{//m_i = 40; //错return m_i;}
private:int m_i;
};
void main()
{A a(30);const A b(50);  //常对象a.print();b.print();cout << a.GetI() << endl;
}

【运行结果】
C++ const的作用
【说明】
(1)函数后面加const可以构成函数重载。
(2)函数后面加const叫做常成员函数,常成员函数在当前函数中不能修改本类数据成员的值。
(3)常对象在调用成员函数的时候调用的是常成员函数,如果是非常对象那么调用的就是非常成员函数。如b调用的是void print()const常成员函数,a调用的是void print()非常成员函数。
①如果没有非常成员函数,那么a也会调用常成员函数void print()const。因为虽然a不是常对象,可以修改也可以不修改,它如果调用常成员函数,虽然常成员函数不能修改数据成员的值,但是并不冲突。所以非常对象可以调用常成员函数。

class A
{
public:A(int i = 0){m_i = i;}//void print() { cout << m_i << endl; }void print()const { cout << "const" << m_i << endl; }
private:int m_i;
};
void main()
{A a(30);const A b(50);  //常对象a.print();b.print();
}

【运行结果】
C++ const的作用
②如果没有常成员函数,那么常对象b不会调用非常成员函数void print()

class A
{
public:A(int i = 0){m_i = i;}void print() { m_i = 10;cout << m_i << endl; }//void print()const { cout << "const" << m_i << endl; }
private:int m_i;
};
void main()
{A a(30);const A b(50);  //常对象a.print();b.print();
}

以上代码不能执行,因为b是const类型的,如果可以调用非常成员函数,那么在非常成员函数中会存在修改m_i的情况,但是b是const类型的就意味着不可以修改m_i的值,这两者冲突。所以常对象不能调用非常成员函数。