C++类中成员变量初始化

来源:互联网 发布:淘宝怎么认证全球购 编辑:程序博客网 时间:2024/05/22 16:34
C++类中成员变量包括主要四种:
普通成员变量,常量成员变量,静态成员变量,静态常量成员变量

上述成员变量该如何初始化,注意不是赋值。
由于普通成员变量和常量成员变量,每一个类实例化,都一份内存拷贝。C++规定成员变量在声明(注意声明与定义区别)时,不允许初始化,因此这些变量只能放在构造函数初始化列表中。
静态成员变量所有类实例化,只有一份内存拷贝,不能放在构造函数中初始化, 因为共享一份内存。同时C++规定成员变量在声明(注意声明与定义区别)时,不允许初始化。所以只能定义时初始化。

静态常量成员变量比较特殊化,即不能放在构造函数初始化列表中,也不能定义时初始化,那么只能在声明(注意声明与定义区别)时,初始化。

声明与定义简单区别,声明不分配内存,定义分配内存。类没有产生对象,那么成员变量没有分配内存的,所有其成员变量为声明。注意与C语言区别,C语言变量有时即是定义有时声明, 例如int a;


另外常量成员函数,不能改变成员变量,例如赋值操作,但是可以改变局部变量。

using namespace std;
#include<iostream>
class Test{
private:
        int i;//声明普通成员
        const int j;//声明常量成员
public:
        static int k;//声明静态成员
        static  const int m = 1; //声明静态&&常量初始化
        Test(int val):i(val),j(val) //普通成员,常量成员初始化
        {
        }
        int getval() const
        {
                //i=5555;
                return j;
        }

};

int Test:: k=2; //定义静态成员初始化
int main()
{
        int c;
        Test test(3);
        cout<<"const:"<<test.getval();
        cout<<"static:"<<Test::k;

        cout<<"const&static"<<Test::m;

}





const成员、引用成员初始化必须在构造函数的初始化列表中进行
    实例如下:
 
TEST_1.h
 
  1. # ifndef _TEST_H_ 
  2. # define _TEST_H_ 
  3.  
  4. class Object 
  5.  
  6. public
  7.     enum E_TYPE 
  8.      {//对所有对象来说都是常量 
  9.           TYPE_A = 100,   
  10.           TYPE_B = 200 
  11.      };  
  12. public
  13.     Object(int num);         
  14.     ~Object(); 
  15.  
  16.     void DisplayKNum(); 
  17.      
  18. private
  19.     int num_; 
  20.     const int kNum_;//仅限于某个对象是常量 
  21.     int& refNum_; 
  22. }; 
  23. # endif //_TEST_H_ 
TEST_1.cpp
 
  1. # include "Test_1.h" 
  2. # include <iostream> 
  3. using namespace std; 
  4.  
  5. Object::Object(int num = 0) : num_(num),kNum_(num_),refNum_(num_) 
  6. {  //本质上是赋值 
  7.          //Knum = 100; error const的初始化必须在初始化列表中初始化 
  8.          //refNum_ = num_; error 引用成员的初始化必须在初始化列表中初始化 
  9.            cout << "Object "<<num_ << "..." << endl; 
  10.  
  11.  
  12.  
  13. void Object::DisplayKNum() 
  14.         //cout << "kNum = " << kNum_ << endl; 
  15.         cout << "kNum = " << kNum_ << endl; 
  16.  
  17. Object::~Object() 
  18.         cout << "~Object "<<num_<<"..." << endl; 
main.cpp
 
  1. #include "Test_1.h" 
  2. # include <iostream> 
  3. using namespace std; 
  4.  
  5.  
  6. int main(void
  7.     Object obj1(10); 
  8.     Object obj2(20); 
  9.  
  10.     obj1.DisplayKNum(); 
  11.     obj2.DisplayKNum(); 
  12.      
  13. //针对类内部是常量,而对于所有对象都是常量要用枚举   
  14.     cout <<obj1.TYPE_A<<endl; 
  15.     cout <<obj2.TYPE_A<<endl<<endl; 
  16. //适用于任何对象,要用枚举常量 
  17.     cout <<Object::TYPE_A<<endl; 
  18.     cout <<Object::TYPE_B<<endl; 
  19.      
  20.     return 0; 
运行结果:






有关const成员、static成员、const static成员的初始化:

 

1、const成员:只能在构造函数后的初始化列表中初始化

2、static成员:初始化在类外且不加static修饰

3、const static成员:类只有唯一一份拷贝,且数值不能改变。因此,可以在类中声明处初始化,也可以像static在类外初始化

 

示例:

[cpp] view plaincopy
  1. #include <iostream>  
  2. using std::cout;  
  3. using std::endl;  
  4. class base  
  5. {  
  6. public:  
  7.     base(int x=8):a(x){}//const成员在构造函数初始化  
  8.     const int a;  
  9.     static int b;  
  10.     const static int c=9;//const static成员在类内初始化  
  11. };  
  12. int base::b=9;//static成员在类外初始化,可以修改  
  13. //const int base::c=10;//也可以像static在类外初始化  
  14. int main()  
  15. {  
  16.     base obj;  
  17.     cout<<obj.a<<endl;  
  18.     cout<<base::b<<endl;  
  19.     cout<<base::c<<endl;  
  20. }  
 



特殊数据类型成员变量的初始化  

有些成员变量的数据类型比较特别,它们的初始化方式也和普通数据类型的成员变量有所不同。这些特殊的类型的成员变量包括:

a.       常量型成员变量

b.       引用型成员变量

c.        静态成员变量

d.       整型静态常量成员变量

e.       非整型静态常量成员变量

 

对于常量型成员变量和引用型成员变量的初始化,必须通过构造函数初始化列表的方式进行。在构造函数体内给常量型成员变量和引用型成员变量赋值的方式是行不通的。

 

静态成员变量的初始化也颇有点特别。

 

参考下面的代码以及其中注释:

// Initialization of Special Data Member

#include <iostream>

using namespace std;

 

class BClass

{

public:

         BClass() : i(1), ci(2), ri(i)   // 对于常量型成员变量和引用型成员变量,必须通过

         {                                             // 参数化列表的方式进行初始化。在构造函数体内进

         }                                             // 行赋值的方式,是行不通的。

 

         void print_values()

         {

                   cout << "i =\t" << i << endl;

                   cout << "ci =\t" << ci << endl;

                   cout << "ri =\t" << ri << endl;

                   cout << "si =\t" << si << endl;

                   cout << "csi =\t" << csi << endl;

                  cout << "csi2 =\t" << csi2 << endl;

                   cout << "csd =\t" << csd << endl;

         }

private:

         int i;                                                          // 普通成员变量

         const int ci;                                             // 常量成员变量

         int &ri;                                                      // 引用成员变量

         static int si;                                             // 静态成员变量

         //static int si2 = 100;                             // error: 只有静态常量成员变量,才可以这样初始化

         static const int csi;                                // 静态常量成员变量

         static const int csi2 = 100;                   // 静态常量成员变量的初始化(Integral type)    (1)

         static const double csd;                      // 静态常量成员变量(non-Integral type)

         //static const double csd2 = 99.9;      // error: 只有静态常量整型数据成员才可以在类中初始化

};

 

// 静态成员变量的初始化(Integral type)

int BClass::si = 0;

// 静态常量成员变量的初始化(Integral type)

const int BClass::csi = 1;

// 静态常量成员变量的初始化(non-Integral type),只能在类外部初始化,且要去掉static

const double BClass::csd = 99.9;

 

// 在初始化(1)中的csi2时,根据Stanley B. Lippman的说法下面这行是必须的。

// 但在VC2003中如果有下面一行将会产生错误,而在VC2005中,下面这行则可有可无,这个和编译器有关。

const int BClass::csi2;

 

int main(void)

{

         BClass b_class;

         b_class.print_values();

 

         return 0;

}



0 0
原创粉丝点击