C++——初始化列表

我们已经知道const变量在C++里成了真正意义上的常量了,const变量的值保存在符号表里,虽然某些操作也会为其分配内存,但是值并不会保存在那块分配的内存。既然是常量,所以我们不能在程序里作为左值,所以必须在定义的时候就初始化,但是类成员变量粗了static const int成员变量,其他类型的都只能定义,不能定义的时候初始化,那么我们可以在类里提供一个const类型的成员变量嘛?编译器是允许呢!

那我们在哪里初始化const类型的成员变量呢?难道在构造函数中嘛,肯定不行,const不能是左值啊。所以就引出了我们今天的主角,初始化列表。

当然初始化列表可以对任何一个成员变量进行初始化,不仅仅是const类型的成员变量。

初始化列表是在构造函数的函数体之前执行的操作。而且比较有趣的是,初始化的顺序并不是按照初始化列表中的出现顺序,而是由成员变量声明的顺序决定的。通过一小段代码说明。

class Test
{
    int a;
    int b;
    const int c;

public:
    Test():c(0),b(0)
    {
        a = 0;
    }
};

在这里使用了初始化列表对一部分成员变量进行了初始化,这里不考虑a的初始化了,因为它是在构造函数内部,此时初始化列表已经执行完操作了。初始化列表首先出现的是c,其次是b,但是按照声明的顺序,是b先被初始化为0,然后c被初始化0。此时a并没有初始化,如果列表中有a,不管第几个出现,一定是第一个被初始化的。

看似到这里都Ok了,其实并没有。因为在编译的时候const类型的成员变量没有初始值,所以无法进入常量表成为真正的常量。类中的const类型成员变量会分配内存,只是c语言中意义上的具有只读属性的变量,说到底类中的const类型变量还是变量,而不是常量,可以通过强制转换为非const指针或引用修改。这就真正叙述完了。

### 关于C++初始化列表的练习题及解答 #### 练习题1:理解并应用初始化列表 题目描述如下: 设计一个`Rectangle`矩形类,该类具有两个私有属性——长度和宽度。通过构造函数使用初始化列表来设置这些属性,并提供获取这两个属性的方法。 ```cpp #include <iostream> using namespace std; class Rectangle { private: double length; double width; public: // 使用初始化列表的构造函数 Rectangle(double l, double w) : length(l), width(w) {} // 获取长度的方法 double getLength() const { return length; } // 获取宽度的方法 double getWidth() const { return width; } }; void printRectangleInfo(const Rectangle& rect) { cout << "Length: " << rect.getLength() << ", Width: " << rect.getWidth() << endl; } int main() { Rectangle r(10.5, 20.5); printRectangleInfo(r); return 0; } ``` 此代码展示了如何利用初始化列表在构造函数中直接初始化成员变量[^1]。 #### 练习题2:结合默认参数与初始化列表 题目要求扩展上述`Rectangle`类,在保持原有功能的基础上增加一个新的构造函数,允许只指定其中一个维度,默认另一个维度为特定值(比如宽度设为1)。同样采用初始化列表完成这一操作。 解决方案可以在原基础上添加新的构造函数重载形式: ```cpp // 添加带有默认参数的新构造函数 Rectangle(double l = 1, double w = 1) : length(l), width(w) {} ``` 这样即使调用者仅提供了单个参数,也能正常创建对象实例[^2]。 #### 练习题3:处理复杂类型的初始化 考虑更复杂的场景,假设有一个名为`Person`的人类模型,它不仅包含了基本的数据类型作为其字段,还可能拥有指向其他对象或容器类型的成员变量。此时应优先选用初始化列表来进行高效且安全的对象构建。 例如,如果`Person`拥有一组联系方式,则可以通过初始化列表一次性为其分配空间并填充初始数据: ```cpp #include <vector> #include <string> class Person { private: string name; vector<string> contactNumbers; public: // 构造函数使用初始化列表初始化name和contactNumbers Person(const string& n, const initializer_list<string>& numbers) : name(n), contactNumbers(numbers) {} void displayContacts() const { for (const auto& num : contactNumbers) { cout << num << ' '; } cout << '\n'; } }; ``` 这段代码片段说明了当涉及到集合或其他复合结构时,初始化列表能够简化编码过程的同时提高性能[^3]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值