C++深度解析(12)—初始化列表的使用、类中的const成员、const对象

1.C++中的对象组合

  • C++中的类可以使用其它类定义成员变量,如何给对象成员进行初始化?
  • C++中提供了初始化列表对成员变量进行初始化
//语法规则
ClassName::ClassName (): ml(vl), m2(vl,v2), m3(v3)  
{  
    //some other initialize operation  
}   
  • 注意事项 
    • 成员的初始化顺序与成员的声明顺序相同 
    • 成员的初始化顺序与初始化列表中的位置无关 
    • 初始化列表先于构造函数的函数体执行 
#include 

class M
{
private:
    int mI;

public:
    M(int i)
    {
        printf("M(int i), i = %d\n", i);
        mI = i;
    }
    
    int getI()
    {
        return mI;
    }
};

class Test
{
private:
    const int c;
    M m1;
    M m2;

/*
成员变量的初始化顺序与声明的顺序相关,
与在初始化列表中的顺序无关
初始化列表先于构造函数的函数体执行
*/
public:
	Test() : c(1), m2(3), m1(2)  // 初始化列表,用法:对象名(构造函数的参数)
	{ 
		printf("Test()\n");
	}

	void print()
	{
		printf("c = %d, m1.mI = %d, m2.mI = %d\n", c, m1.getI(), m2.getI());
	}
};


int main()
{
	Test t1;
	t1.print();

	printf("Press any key to continue...");
    
	getchar();
    
	return 0;
}
  • 运行结果:

2. 类中的const成员、const对象

//类中是否可以定义const成员?
#include 
 
class Test
{
private:
    const int ci;//error: uninitialized const member in ‘const int’ ,‘const int Test::ci’ should be initialized

public:
    Test()
    {
        ci = 10;//error: assignment of read-only member ‘Test::ci’
    }
    
    int getCI()
    {
        return ci;
    }
};
 
int main()
{
    Test t;
 
    printf("t.ci = %d\n", t.getCI());
 
    return 0;
}
  • 类中的const成员会被分配空间的 
  • 类中的const成员变量的本质是只读变量 
  • 类中的const成员变量只能在初始化列表中指定初始值 (引用数据成员也是)
  • 编译器无法直接得到const成员的初始值,因此无法进入符号表成为真正意义上的常量。

2.1初始化与赋值不同 

  • 初始化:对正在创建的对象进行初值设置 
  • 赋值:对已经存在的对象进行值设置 

2.2 const成员变量

#include 

class Value
{
private:
	int mi;

public:
	Value(int i)
	{
		printf("i = %d\n", i);
		mi = i;
	}

	int getI()
	{
		return mi;
	}
};

class Test
{
private:
	const int ci;
	Value m2;
	Value m3;
	Value m1;

public:
	Test() : m1(1), m2(2), m3(3), ci(100)
	{
		printf("Test::Test()\n");
	}
	
	int getCI()
	{
		return ci;
	}
	
	void setCI(int v)
	{
		int *p = const_cast(&ci);

		*p = v;
	}
};

int main()
{
	Test t;

	printf("t.ci = %d\n", t.getCI());

	t.setCI(10);

	printf("t.ci = %d\n", t.getCI());

	getchar();
	
	return 0;
}
  • 运行结果:

2.2 const对象

  • const关键字能够修饰对象 
  • const修饰的对象为只读对象 
  • 只读对象的成员变量不允许被改变 
  • 只读对象是编译阶段的概念,运行时无效 

2.3 const成员函数

  • const对象只能调用const的成员函数 
  • const成员函数中只能调用const成员函数 
  • const成员函数中不能直接改写成员变量的值
  • const成员函数的定义:Type ClassName::function(Type p) const 
  • 类中的函数声明与实际函数定义中都必须带const关键字
#include 

using namespace std;

class Test
{
public:
	int ci;

	Test() :ci(1)
	{
	
	
	}

	int getCI() const   //本质:const成员函数 ==> const Test* const this
	{
		return ci;
	}

	void print()
	{
		cout << "我是非const成员函数" << endl;
	}
};

int main()
{
	Test t;

	cout << t.getCI() << endl;   // 1

	const Test tt;   // const对象

	cout << tt.getCI() << endl;// 1
	//tt.print();//error: 'this' argument to member function 'print' has type 'const Test', but function is not marked const

	Test *ptt = const_cast(&tt);

	ptt->ci = 5;
	cout << ptt->getCI() << endl; // 5
	ptt->print();

	getchar();

	return 0;
}
  • 运行结果:

3.小结            

  • 类中可以定义const成员变量 
  • const成员变量必须在初始化列表中指定初值 
  •  const成员变量为只读变量 
  • const关键字能够修饰对象,得到只读对象 
  • 只读对象只能调用const成员函数 

你可能感兴趣的:(c++深度剖析)