[英]Overloaded operator is never called in C++
I'm writing a math library as a practical exercise. 我正在写一个数学库作为练习。 I've run into some problems when overloading the = operator.
重载=运算符时,我遇到了一些问题。 When I debuged it, I noticed that the call to vertex1 = vertex2 calls the copy constructor instead.
当我调试它时,我注意到对vertex1 = vertex2的调用改为调用了复制构造函数。
In the header file I have: 在头文件中,我有:
//constructors
vector3();
vector3( vector3 &v );
vector3(float ix, float iy, float iz);
//operator overloading
vector3 operator =(vector3 p);
....
In the source file I implemented: 在源文件中,我实现了:
vector3 vector3::operator =(vector3 p)
{
vector3 v3;
v3.x = p.x;
v3.y = p.y;
v3.z = p.z;
return v3;
}
Later on I have a crossproduct method, and I want to use it like so: 稍后我有一个叉积方法,我想这样使用它:
vector3 v3;
v3 = v1.crossProduct(v2);
The error message is: error: no matching function for call to `vector3::vector3(vector3)' but I do not want to call the copy constructor. 错误消息是:错误:没有匹配的函数来调用`vector3 :: vector3(vector3)',但是我不想调用复制构造函数。
There are mistakes in your code. 您的代码中有错误。 Your copy-constructor must take a
const&
. 您的复制构造函数必须采用
const&
。 The reference will avoid making a copy (which you wouldn't be able to do, being the copy-constructor), and it should be const
since you're not modifying it: 该参考将避免制作副本(您将无法复制,成为副本构造函数),并且它应该是
const
因为您没有对其进行修改:
vector3(const vector3&);
Temporary variables can be bound to const&
, but cannot be bound to a mutable reference. 临时变量可以绑定到
const&
,但不能绑定到可变引用。 That is, with your code you could do: 也就是说,使用您的代码,您可以执行以下操作:
vector3 a;
vector3 b(a);
but not: 但不是:
vector3 a(some_calculation()); // some_calculation returns a vector3
Additionally, your operator=
is incorrect. 此外,您的
operator=
错误。 Like the copy-constructor, it should generally take a const&
, but it should return a reference to this
. 像copy-constructor一样,它通常应采用
const&
, 但应返回this
的引用 。 That's how chaining works: 这就是链接的工作方式:
int a, b, c;
a = b = c = 0;
// a.operator=(b.operator=(c.operator=(0)));
Returning a temporary is unorthodox, and doesn't accomplish anything. 返回一个临时值是非正统的,并且不会完成任何事情。 In your case, you could assign over and over and never change the value.
在您的情况下,您可以反复分配并且永远不要更改该值。 Weird :
奇怪 :
vector 3 a, b;
a = b; // doesn't change a...?!
operator=
needs to change this
. operator=
需要更改this
。
vector3( vector3 &v );
vector3(vector3&v);
That really should be vector3( const vector3 &v );
那真的应该是
vector3( const vector3 &v );
Since your return a temporary value, you must call a copy-constructor which takes a const reference. 由于返回的是一个临时值,因此必须调用采用const引用的copy-constructor。
I do not want to call the copy constructor.
我不想调用复制构造函数。
What you want is irrelevant. 您想要的与您无关。 You need a copy constructor here.
您在这里需要一个复制构造函数。
operator =
doesn't get called in this situation, the copy constructor is. 在这种情况下,不会调用
operator =
,而复制构造函数是。 Besides, the signature is wrong, it should be 此外,签名是错误的,应该是
vector3& operator =(vector3 const& other);
The argument may also be passed in by value (but this is an advanced trick …) but the return value really must be a non-const reference. 参数也可以按值传递(但这是一个高级技巧……),但是返回值确实必须是非常量引用。
(The signature of your copy constructor is also unconventional, see James' answer.) (您的副本构造函数的签名也不是常规的,请参阅James的回答。)
Make vector3 vector3::operator =(vector3 p)
use references instead so you don't need to create a copy. 使
vector3 vector3::operator =(vector3 p)
改为使用引用,因此您无需创建副本。
vector3& vector3::operator =(vector3& p);
You didn't want to create a copied object in the first place anyway. 无论如何,您根本不想创建复制的对象。
It is good practice in C++ to do one of two things depending on whether you want your object copyable (ie assignable to another variable) or not. 在C ++中,根据您是否希望对象可复制(即可分配给另一个变量)来执行以下两项操作之一是一种好习惯。 If you do you need to provide both the assign operator and the copy constructor.
如果需要,则需要同时提供assign运算符和副本构造函数。 For example:
例如:
class Point
{
public:
Point () { }
Point (int x, int y) : mX(x), mY(y) { }
Point (const Point& p) : mX(p.mX), mY(p,mY) { }
Point& operator = (const Point& p) { mX = p.mX; mY = p.mY; return *this; }
int X () const { return mX; }
int Y () const { return mY; }
private:
int mX;
int mY;
};
If you don't want it copyable you can put the prototype of both the copy constructor and the assign operator in a private section and do not provide an implementation. 如果您不希望它可复制,则可以将复制构造函数和assign运算符的原型放在专用部分中,而不提供实现。 Any attempt to copy it then will give a compiler error.
任何尝试复制它的操作都会产生编译器错误。
Whenever you use this kind of code: 每当您使用这种代码时:
Point P = anotherP;
the copy constructor will be called. 复制构造函数将被调用。 If you use this type of code:
如果您使用这种类型的代码:
Point P;
P = anotherP;
the assign operator will be called. 分配运算符将被调用。
Hope that helps. 希望能有所帮助。
When you "pass by value", as you are in your definition of operator =, a copy of the type is made for use a as local value to the method. 当您按值传递时(如您在operator =的定义中一样),将创建该类型的副本以用作方法的局部值。 Your operator isn't being called because the system cannot find a contructor that takes vector3 -- you've defined a copy constructor that takes vector3&.
不会调用您的运算符,因为系统无法找到采用vector3&的构造函数-您已定义了采用vector3&的副本构造函数。
Therefore, as others have stated, what you want to do is define your operator = as taking 因此,正如其他人所述,您想要做的就是定义您的运算子=
const vector3& p
You should also update your declared copy constructor to take const vector3 also. 您还应该更新声明的副本构造函数以也采用const vector3。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.