【问题标题】:Reference initialization as member of class引用初始化作为类的成员
【发布时间】:2015-02-21 17:17:43
【问题描述】:

我有“段”类:

class Segment
{
private:
    Point &_a;
    Point &_b;
public:
    Segment(const Point& start, const Point& end);
    ~Segment(); 
};

这是构造函数的实现:

Segment::Segment(const Point& start, const Point& end): 
    _a(Point(start.x(), start.y())), 
    _b(Point(end.x(), end.y())), 
    _segmentID(_freeID++)
    {
        return;
    }

它符合警告:

警告 C4413:引用成员被初始化为在构造函数退出后不会持续存在的临时对象

如何正确初始化类构造函数中的引用?如何摆脱这个警告?

附:这是另一个有同样问题的构造函数:

Segment::Segment(double x1, double y1, double x2, double y2): 
    _a(Point(x1, y1)), 
    _b(Point(x2, y2)),
    _segmentID(_freeID++)
    {
        return;
    }

【问题讨论】:

  • 为什么要使用参考成员?为什么不只是普通的成员变量?

标签: c++ class reference member


【解决方案1】:

你的问题是这样的。

Segment::Segment(const Point& start, const Point& end): 
    _a(Point(start.x(), start.y())), 
    _b(Point(end.x(), end.y())), 
    _segmentID(_freeID++)
    {
        return;
    }

在您的初始化列表中,您正在创建一个临时对象。

Point(start.x(), start.y())

一旦退出创建它的范围,这个临时对象就会被销毁,这就是您引用的错误消息告诉您的内容。

您可以将初始化程序更改为以下内容:

Segment::Segment(Point& start, Point& end): 
    _a(start), 
    _b(end), 
    _segmentID(_freeID++)
    {
    }

问题在于 _a 和 _b 的生命周期是你无法控制的。如果这些是基于堆栈的变量,那么它们可能会在您的对象仍然依赖它们作为有效变量时被销毁。

另外,构造函数的返回是没有意义的。

【讨论】:

  • 谢谢!有用。我对另一个构造函数有同样的问题,你能帮我吗? [代码]Segment::Segment(double x1, double y1, double x2, double y2): _a(Point(x1, y1)), _b(Point(x2, y2)), _segmentID(_freeID++) { return; } [代码]
  • 你和你之前的构造函数有同样的问题。你读过弗雷迪的解释吗?还是您只是复制/粘贴是解决方案?
【解决方案2】:
Segment::Segment(const Point& a, const Point& b) :
    _a(a), _b(b), _segmentID(_freeID++) { }

用于构造SegmentPoints 必须与Segment 一样长,因为它保留对它的引用。

Point(start.x(), start.y()) 会构造一个新的(临时)Point 对象,但使用它来初始化引用是无效的,因为临时对象会立即超出范围。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-12-08
    • 1970-01-01
    • 2011-04-02
    • 2015-04-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多