object construction : default parameter vs delegation
考虑以下代码,在这里我尝试引入默认构造函数以及
1 2 3 4 5 6 7 8 | class A { private: unsigned int count; public: A(int new_c) : count(new_c) {} A() : A(10) {} }; |
与在参数化构造函数上设置默认参数并完全忽略默认构造函数的旧方法相比。
1 2 3 4 5 6 7 | class A { private: unsigned int count; public: A(int new_c = 5) : count(new_c) {} }; |
与遵循第二种约定相比,使用第一种方法要比第二种方法有什么优势吗?
在功能上没有区别。要知道,非静态成员初始化还有另一个选项可用(自C 11起):
1 2 3 4 5 6 7 8 | class A { private: unsigned int count = 10; public: A() = default; A(int new_c) : count(new_c) {} }; |
在您的示例中,这种情况没有任何优势(在该示例中,我甚至会选择第二个选项,以便更清楚地了解该问题)
在默认值不足的情况下添加的委托构造函数,以简化工作。
例如
1 2 3 4 5 | struct Point3d { Point3d(int x, int y, int z); Point3d(Point2d p) : Point3d(p.x, p.y, 0) {} } |
从技术上讲没有区别,但是创建转发构造函数的想法却不同。
想象一下下面的类:
1 2 3 4 5 6 7 8 9 10 11 12 | class sample { complexType member; bool createdWithInt; public: sample() : member(5), createdWithInt(false) { /* code ... */ } sample(int param) : sample() { createdWithInt = true; /* other code */ } }; |
因此,此类很难使用默认参数实现:
其行为不取决于参数的值,而取决于存在性。
可能会尝试使用一个辅助函数
注意:
在较大的类(可以是几个构造函数)的情况下,优势会更加明显。用新的方式,您将能够编写一个构造函数,然后将其设置为其他构造函数。这不太容易出错。
1 2 3 4 5 6 7 8 9 10 11 12 | class A { private: unsigned int count; int other; float otherfloat; public: A( unsigned int count, int other, float otherfloat ) : count( count), other( other ), otherfloat( otherfloat ) {} A(int new_c) : A(new_c, 0, 0.0 ) {} A() : A(10) {} }; |