2015-11-07 2 views
2

У меня странная ошибка, когда я пытаюсь скомпилировать этот фрагмент кода. Я объясню свою проблему.
я определил vector2D следующим образом:проблема с комбинацией: оператор '==' и оператор '-'

typedef struct LX_Vector2D 
{ 
    float vx; 
    float vy; 

    LX_Vector2D& operator =(const LX_Vector2D v); // Defined 

} LX_Vector2D; 

Я также определил два оператора на этом векторе:

bool operator ==(LX_Vector2D& u,LX_Vector2D& v); // Are u and v equal? 
LX_Vector2D operator -(LX_Vector2D& u);   // Get the opposite vector 

Все эти перегруженных операторов была определена.
Так я тестировал эти операторы в следующем коде:

LX_Vector2D u = {3.14,-2.56}; 
LX_Vector2D expected_vec = {-u.vx,-u.vy}; 

if(expected_vec == (-u)) // ERROR 
    cout << "OK" << endl; 
else 
    cout << "NO" << endl; 

Когда я скомпилировать этот код, у меня есть эта ошибка:
нет ровня «оператора ==» в «expected_vec == operator- ((* & и))»

у меня нет никаких проблем с„=“и„==“, потому что я определил и протестировали их, прежде чем я осуществил„-“.

Но когда я изменить этот код, чтобы получить это:

u = -u; 
if(expected_vec == u) // OK 

У меня нет ошибки. Я этого не понимаю, потому что кажется, что эти два фрагмента кода семантически идентичны.

Вот определение оператора '-':

LX_Vector2D operator -(LX_Vector2D& u) 
{ 
    return {-u.vx,-u.vy}; 
} 

Так что мой вопрос:
Почему не мой компилятор признает 'expected_vec == (-u)' как звонок оператор '==' с expected_vec и (-u) как параметры?

Другой вопрос:
Как я могу иметь возможность использовать если (expected_vec == (-u)) без каких-либо проблем, если это возможно?

Я использую g ++ 4.6.1.

+0

Не могли бы вы отредактировать свой вопрос, включив в него * полный вывод ошибки, потому что то, что вы показываете нам, должно быть не всем. –

+1

Не могли бы вы рассказать нам, кто научил вас говорить «typedef struct», чтобы мы могли создать большую зону карантина вокруг этого человека? –

+0

Не имеет прямого отношения к вашему вопросу, но ваше задание должно принимать const-ссылку. В настоящее время он передается по значению. Кроме того, я думаю, что ваш оператор должен вернуть ссылку. –

ответ

4

Проблема здесь состоит в том, что результат от operator- при использовании в качестве части другого выражения является временным значением, и что operator== принимает непостоянную ссылку. Ссылка на константу не может привязываться к временному значению.

Простое решение? Сделайте функцию operator== принимать постоянные ссылки:

bool operator ==(const LX_Vector2D& u, const LX_Vector2D& v) 
//    ^^^^^     ^^^^^ 
// Note the use of `const` 

В качестве общей рекомендации, при объявлении функции, которые не будут изменять свои аргументы, всегда передавать аргументы постоянная. Это позволит избежать подобных проблем, а также может помочь компилятору с возможной оптимизацией.

3

Оператор - возвращает временный объект:

LX_Vector2D operator -(LX_Vector2D& u) 

в то время как ваш оператор сравнения принимает не- const ссылка:

bool operator ==(LX_Vector2D& u,LX_Vector2D& v) 

Временные объекты, как возвращаемый оператором -, не может быть использован в качестве не const ссылок. Это не допускается, потому что нет цели, изменяющей объект, который все равно выходит из области видимости, поэтому компилятор убеждается, что вы даже не пытаетесь его выполнить.

Как правило, вы должны делать какую-либо функцию, которая не изменяет ее аргументы принимают const ссылок вместо этого, особенно функции сравнения:

bool operator ==(const LX_Vector2D& u,const LX_Vector2D& v) 
0

в дополнении к другим ответам, ваш оператор присваивания должен также взять const& как в:

LX_Vector2D& operator =(const LX_Vector2D& v) 

записке & после типа параметра.

Как правило, и чтобы избежать создания ненужных копий объектов, параметры сложных типов должны быть всегда всегда const &, если вы не планируете изменять экземпляр параметра. Или если вы планируете изменить экземпляр параметра, то просто как ссылку, то есть &.

Смежные вопросы