为什么要调用用于初始化另一个对象的对象的复制构造函数


class point
{
public:
point(double x, double y) : x(x), y(y)
{
std::cout << "point parameterized constructor of: "
<< getThis() << std::endl;
}
point(const point& that) : x(that.x), y(that.y)
{
std::cout << "point copy constructor of: "
<< getThis() << std::endl;
}
~point()
{
std::cout << "point destructor of: "
<< getThis() << std::endl;
}
private:
double x;
double y;
point* getThis() { return this; }
};
class line
{
public:
line(const point& startPoint, const point& endPoint) :
startPoint(startPoint)
endPoint(endPoint)
{
std::cout << "line parameterized constructor: " << getThis() << std::endl;
}
~line()
{
std::cout << "line destructor of: "
<< getThis() << std::endl;
}
private:
point startPoint;
point endPoint;
line* getThis() { return this; }
};
int main()
{
point p1(3.0, 4.0);
point p2(5.0, 6.0);
line l1(p1, p2);
return 0;
}

程序输出:

point parameterized constructor of: 0x577fffc00
point parameterized constructor of: 0x577fffbe0
point copy constructor of: 0x577fffbb0
point copy constructor of: 0x577fffbc8
lineSegment parameterized constructor of: 0x577fffbb0
lineSegment destructor of: 0x577fffbb0
point destructor of: 0x577fffbc8
point destructor of: 0x577fffbb0
point destructor of: 0x577fffbe0
point destructor of: 0x577fffc00

我不明白point的复制构造函数是如何被调用2次的(每个点参数1次(原因是最初,行构造函数参数不是const引用。编译器对行构造函数发出了警告

Clang-Tidy: The parameter 'endPoint' is copied for each invocation but only used as a const reference; consider making it a const reference
line(point startPoint, point endPoint) : startPoint(startPoint), endPoint(endPoint) {...}

这就是输出:

point parameterized constructor: 0x8feedffa40
point parameterized constructor: 0x8feedffa20
point copy constructor: 0x8feedffa60
point copy constructor: 0x8feedffa80
point copy constructor: 0x8feedff9f0
point copy constructor: 0x8feedffa08
lineSegment parameterized constructor: 0x8feedff9f0
point destructor: 0x8feedffa80
point destructor: 0x8feedffa60
lineSegment destructor: 0x8feedff9f0
point destructor: 0x8feedffa08
point destructor: 0x8feedff9f0
point destructor: 0x8feedffa20
point destructor: 0x8feedffa40

正如您所看到的,点的复制构造函数被调用4次(每个点参数2次(。当我进行参数const点引用时,我假设所有4个调用都会消失。相反,他们减少了一半。为什么?

line类的构造函数中

line(const point& startPoint, const point& endPoint) :
startPoint(startPoint)
endPoint(endPoint)
{
std::cout << "line parameterized constructor: " << getThis() << std::endl;
}

在这个mem初始化器列表中,为数据成员startPointendPoint使用了类型为point的复制构造函数

startPoint(startPoint)
endPoint(endPoint)

在此构造函数中

line(point startPoint, point endPoint) : startPoint(startPoint), endPoint(endPoint) {...}

在参数不被引用接受的情况下,复制构造函数会被多次调用以初始化参数。

最新更新