zoukankan      html  css  js  c++  java
  • C++学习之路—const用法总结

    (根据《C++程序设计》(谭浩强)整理,整理者:华科小涛,@http://www.cnblogs.com/hust-ghtao转载请注明)

        C++为什么要引入const?它允许你指定一个语义约束(也就是指定一个“不该被改动”的对象),而编译器会强制实施这项约束。它允许你告诉编译器和其他程序员某值应该保持不变。只要这是事实,你就该确实说出来,因为说出来可以获得编译器的襄助,确保这条约束不被违反。另外,C++虽然采取了不少有效的措施(如设private保护)以增加数据的安全性,但是有些数据往往是共享的,例如实参与形参,变量与其引用,数据及其指针等,人们可以在不同的场合通过不同的途径访问同一个数据对象。有时在无意之中的操作会改变有关数据的状况,而这是人们不希望出现的。既要使数据能在一定范围内共享,又要保证它不被任意修改,这时可以把有关的数据定义为常量

    1. 修饰指针

        可以指定指针变量是一个常量,或者指针变量指向的对象是一个常量。有下面几种情况:

    1.1 指向常量的指针变量

        一般形式:const 类型名* 指针变量名不允许通过指针变量改变它指向的对象的值。例如:

       1: int a = 12 , b = 15 ;
       2: const int* p = &a ;
       3: *p = 15 ; // 试图通过p改变它指向的对象的值,非法

    不能通过指针来改变所指对象的值,但是直接改变对象的值是合法的:

       1: a = 15 ;

    另外,指针变量的值是可以改变的:

       1: p = &b ;

    用指向常量的指针变量只是限制了通过指针改变它指向的对象的值 。如果要想绝对保证对象的值始终不变,应当把它定义为常变量:

       1: const int a = 15 ;
       2: const int* p = &a ; /*此时,指针必须为const int * ,因为&a的类型就是const int * ,否则会出错。*/
    无论用直接访问方式或间接访问方式都无法改变对象的值。
        指向常量的指针变量常用于作函数形参,以防止指针形参所指对象的值改变影响实参。

    1.2 常指针变量         

       一般形式:类型名* const 指针变量名指定指针变量的值是常量,即指针变量的指向不能改变。常指针变量简称常指针,必须在定义时初始化,指定其指向;指针变量的指向不能改变,但其指向变量的值是可以改变的:

       1: int a = 4 ;
       2: int b = 6 ;
       3: int* const p = &a ;
       4: p = &b ; /*试图改变p的指向,不合法*/
       5: *p = 12 ;/*改变p的指向变量的值,合法*/

    1.3 指向常量的常指针

        一般形式:const 基本类型名* const 指针变量名把以上两种作用叠加一起,就是指向常量的常指针变量。指针的指向不可改变,其指向变量的值也不可以通过指针改变。

    3. class中应用

        为了说明问题,先构造一个类:

       1: class Time
       2: {
       3: public:
       4:     int hour ;
       5:     int minute ;
       6:     int sec ;
       7:     void get_time();
       8: };
       9: void Time::get_time()
      10: {
      11:     cout << hour << ":" << minute << ":" << sec << endl ;
      12: }

    3.1 常对象

        一般形式:类名 const 对象名[(实参表)]  或 const 类名 对象名[(实参表)] ,在定义常对象时,必须同时对之初始化,之后不能再改变。在对象的周期内,其所有的数据成员的值都不能被修改。

       1: Time const t1(12,34,46) ;/*定义t1是常对象*/

    说明:

    (1)如果一个对象被声明为常对象,则通过该对象只能调用它的常成员函数,而不能调用该对象的普通成员函数。

       1: const Time t1(10,15,36);
       2: t1.get_time();/*试图调用常对象的普通成员函数,非法!*/

    (2)常成员函数可以访问常对象中的数据成员,但仍然不允许修改常对象中的数据成员。

    3.2 常数据成员

        常数据成员的值是不能改变的。注意:只能通过构造函数的参数初始化表对常数据成员进行初始化,任何其他函数都不能对常数据成员赋值,即使在构造函数中也不行。

       1: const int hour ;//定义hour为常数据成员
       2: Time::Time(int h)
       3: {
       4:     hour = h ;  //非法,不能在构造函数中对常数据成员初始化
       5: }
       6:  
       7: Time::Time(int h):hour(h)
       8: { }  //合法,通过参数初始化表的方式初始化常数据成员
       9:  

    由于常对象的数据成员都是常数据成员,因此在定义对象时,构造函数只能采用参数初始化表对常数据成员进行初始化。

    3.3 常成员函数

        一般形式:类型名 函数名(参数表)const,const是函数类型的一部分,在声明和定义时都要有const,调用时不必。

    前面提到:一般的成员函数可以引用本类中的非const数据成员,也可以修改它们。如果将成员函数声明为常成员函数,则只能引用本类中的数据,而不能修改它们。

    有个重要的表格

    数据成员 非const成员函数 const成员函数
    非const数据成员 引用+修改 引用,不可修改
    const数据成员 引用,不可修改 引用,不可修改
    const对象 不允许 引用,不可修改

        如何利用常成员函数?:

    (1)如果在一个类中,有些数据成员的值允许改变,有些不允许。则可以将不允许改变的声明为const,以保证其值不被改变,可以用非const成员函数引用这些数据成员的值,并修改非const数据成员的值。

    (2)如果要求所有的数据成员都不允许改变,则可以将所有的数据成员声明为const或将对象声明为const(常对象),然后const成员函数引用数据成员。

    (3)如果已经定义了一个常对象,只能调用其中的const成员函数。

  • 相关阅读:
    [CF1042F]Leaf Sets
    [CF1051F]The Shortest Statement
    [洛谷P1792][国家集训队]种树
    [CF484E]Sign on Fence
    [洛谷P2216][HAOI2007]理想的正方形
    [洛谷P4389]付公主的背包
    [洛谷P4726]【模板】多项式指数函数
    服务器上Ubuntu系统安装
    删除ubuntu系统
    Win10下安装Ubuntu16.04双系统
  • 原文地址:https://www.cnblogs.com/hust-ghtao/p/3735941.html
Copyright © 2011-2022 走看看