【问题标题】:Why does this std::function and operator cause a segmentation fault?为什么这个 std::function 和 operator 会导致分段错误?
【发布时间】:2021-01-29 07:25:56
【问题描述】:

我看不出这段代码有什么问题,但它给了我一个段错误。将 std::function 更改为普通函数可以解决问题。删除重载运算符中的加法也可以解决问题。将 Point 构造函数从 const int& 更改为 int 也可以解决问题。但我不明白为什么。 https://onlinegdb.com/Sy32UTllO

#include <iostream>
#include <functional>

struct Point
{
    int x, y;
    Point() {}
    Point(const int& x, const int& y) {}
};
Point operator+(const Point& p1, const Point& p2) { return {p1.x+p2.x, p1.y+p2.y}; }
Point p1, p2;
std::function<const Point&()> fn = []{ return p1; };

int main()
{
    Point p3 = fn() + p2;
    return 0;
}

【问题讨论】:

  • p2 未初始化?
  • 将ctor改为Point() : x{}, y{} {} 保证Point的对象默认初始化。

标签: c++


【解决方案1】:
std::function<const Point&()> fn = []{ return p1; };

因为您没有指定 lambda 的返回值,所以它默认返回它按值。所以fn 试图返回一个临时的引用,这是未定义的行为。

改为这样做:

std::function<const Point&()> fn = []() -> const Point& { return p1; };

【讨论】:

  • 哦。 std::function 没有指定返回类型吗?
  • 我明白了。确实如此,但 lambda 没有。对吗?
  • 将 lambda 和 std::function 视为独立的事物(因为它们是)。 std::function 的返回类型和 lambda 的返回类型不相关。 lambda 按值返回p1,然后std::function 尝试返回对该值的引用。
【解决方案2】:

[]{ return p1; } 按值返回,所以fn() 返回一个悬空引用。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-08-18
    • 1970-01-01
    • 2015-06-12
    • 2016-09-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多