复制构造函数调用无限循环
-
23-09-2019 - |
题
我正在传递一个值以复制构造函数作为参考,但是正在调用无限循环。
这是我的班级:
class Vector2f{
private:
GLfloat x;
GLfloat y;
public:
Vector2f();
Vector2f(const GLfloat _x, const GLfloat _y);
Vector2f(const Vector2f &_vector);
~Vector2f();
};
这是方法的实现:
Vector2f::Vector2f():
x( 0.0f ),
y( 0.0f )
{
DebugLog("Vector2f constructor");
}
Vector2f::Vector2f(const GLfloat _x, const GLfloat _y):
x( _x ),
y( _y )
{
DebugLog("Vector2f constructor(%f, %f)", _x, _y);
}
Vector2f::Vector2f(const Vector2f &_vector):
x( _vector.getX() ),
y( _vector.getY() )
{
DebugLog("Vector2f copy constructor");
}
Vector2f::~Vector2f()
{
}
这是我访问课程的方式:
Vector2f tempVector1 = Vector2f(0.0f, 0.0f);
DebugLog("tempVector1 initialized");
Vector2f tempVector2;
tempVector2 = Vector2f(0.0f, 0.0f);
DebugLog("tempVector2 initialized");
我得到的结果是:
Vector2f constructor(0.000000, 0.000000)
tempVector1 initialized
Vector2f constructor
Vector2f constructor(0.000000, 0.000000)
Vector2f copy constructor
Vector2f copy constructor
Vector2f copy constructor
...
尝试初始化先前创建的对象时,会发生无限循环。如果我尝试将tempvector1复制到tempvector 2中,也会发生无限环路:
Vector2f tempVector2;
tempVector2 = Vector2f(tempVector1);
为什么会发生,如何防止它进入无限循环?
先感谢您。
解决方案
我认为问题在于您的作业操作员。操作员=看起来像?
似乎操作员=以某种方式称他为自我。代码段可能是从运算符=本身的主体中获取的吗?
如果是这样,则解决方案是更改代码(内部运算符=),以便使用复制CTOR。规范形式如下:
Vector2f temp = Vector2f(arg);
swap(*this, temp) // You need to implement a swap method
return *this;
(看 出色的C ++ 由Herb Sutter获取更多细节)
其他提示
这线:
tempVector2 = Vector2f(tempVector1);
将调用操作员=,而不是复制构造函数。您是否在定义操作员=正在做古怪的事情?
另外,您的代码对我来说很好,在Linux上使用G ++ 4.3.2和Mac上的G ++ 4.2.1(在我定义GETX,GETY,转换为debuglog到printf并使用float而不是glfloat之后)。
在第二种情况下,您正在执行任务,而不是构造。您尚未定义自己的复制分配运算符,这意味着编译器将为您提供一个。编译器提供的复制操作员将被隐式地声明为
Vector2f& operator =(const Vector2f& rhs);
请注意,该操作员的唯一参数具有参考到CONST类型。
在您的代码中,您坚持提供 临时rvalue 类型的对象 Vector2f
在作业的右侧。
tempVector2 = Vector2f(0.0f, 0.0f);
这意味着 operator =
用类型的临时rvalue初始化。根据他的语言规范(8.5.3/5),允许编译器在实际附加参考之前,将其随意复制多次。最终,它必须停止复制并最终致电操作员。通常,编译器不会对复制行为发疯(其中大多数根本没有复制),但是在您的情况下,这似乎是问题。由于某种原因,您的编译器被锁定在无限复制循环中,永不停止。我不知道是什么原因引起的。可能是编译器中的错误。
请注意,即使在
tempVector2 = Vector2f(tempVector1);
您仍在以临时rvalue的形式提供右侧。 RVALUE是明确铸造的结果 Vector2f
由于某种原因,您放在那里。我不知道你为什么这样做。如果问题确实存在于编译器中(而不是在代码中您没有显示我们),我敢肯定,如果您这样做
tempVector2 = tempVector1;
任务将在没有任何问题的情况下进行。实际上,如果事实证明是编译器中的一个错误,则可以解决问题:停止将临时人员用作复制构成和复制分配操作员的参数。
在IDE下运行它。在循环中时,按“暂停”按钮。您将确切看到问题是什么。 这就是原因。