2014-04-17 19 views
6

Devo essere in grado di confrontare una delle mie classi (che contiene molto più di un intero) in numeri interi, anche se potrebbe essere un po 'più simile di uguaglianza è abbastanza vicino ...Sovraccarico operatori di confronto per diversi tipi in C++

Come sovraccarico l'operatore di uguaglianza per diversi tipi?

Io fondamentalmente sono una classe come questa

struct MyClass { 
    int start; 
    int middle; 
    int threequarters; 
}; 

e l'operatore di overload

inline bool operator==(const MyClass& lhs, const MyClass& rhs) { 
    return lhs.middle == rhs.middle; 
} 

Così, quando si confrontano con interi ho bisogno di confrontare con la variabile di mezzo pure, ma io sono Non sono sicuro se ho bisogno di due serie di funzioni dell'operatore, una in cui l'intero è lhs e uno in cui l'intero è rh?

+1

Sì, dovresti farlo way - support (int, MyClass) e (MyClass, int). Sebbene tu possa definire uno degli operatori nei termini dell'altro.Un'altra possibilità è di avere un costruttore per MyClass che costruisca da un int - quindi ti servirà solo un operatore (MyClass, MyClass) perché quando il compilatore incontra l'int può promuoverlo come tipo MyClass per l'operatore. – qeadz

+0

Quindi per confrontare MyClass con MyClass e interi con MyClass, avrò bisogno di 3 set di ogni funzione di confronto (18 in totale), anche se la maggior parte di essi farà riferimento ad altri ..? – user3235200

+2

Oppure date alla vostra classe un costruttore di converting 'MyClass (int i): middle (i) {}'. – juanchopanza

risposta

4

Per chiarire dal mio commento, questo sosterrà codice in modo è possibile fornire tutte le varianti di operatori:

inline bool operator==(const MyClass& lhs, const MyClass& rhs) { 
return lhs.middle == rhs.middle; 
} 

inline bool operator==(const int& lhs, const MyClass& rhs) { 
return lhs == rhs.middle; 
} 

inline bool operator==(const MyClass& lhs, const int& rhs) { 
return lhs.middle == rhs; 
} 

E farlo per tutti gli operatori (che fa saltare in aria in una notevole quantità di codice). O se ha senso, è possibile fornire un costruttore che costruisce da int:

struct MyClass { 
MyClass() {} // default 
MyClass(int x) { /* init for an int here */ } 
int start; 
int middle; 
int threequarters; 
}; 

Se si fa questo, allora si avrà bisogno solo la versione MyClass, MyClass per ogni operatore:

inline bool operator==(const MyClass& lhs, const MyClass& rhs) { 
return lhs.middle == rhs.middle; 
} 

perché quando il compilatore vede:

if (5 == my_class) {} 

E 'in realtà fa questo:

if (MyClass(5).operator==(my_class)) {} 
1

Sì, è necessario definire tre operatori == a condizione che la classe non abbia costruttore di conversione per oggetti di tipo int.

inline bool operator==(const MyClass& lhs, const MyClass& rhs) { 
    return lhs.middle == rhs.middle; 
} 

inline bool operator==(const MyClass& lhs, int rhs) { 
    return lhs.middle == rhs; 
} 

inline bool operator==(int lhs, const MyClass& rhs) { 
    return operator ==(rhs, lhs); 
} 
+0

E non dovrei ... const int & rhs .. .? – user3235200

+1

@ user3235200 No non è necessario utilizzare const int &. è sufficiente e meglio usare int. –

0

Sì, avete bisogno di entrambi gli operatori.

bool operator==(const A& a, const int & b) 
{ 
    return a.value == b; 
}; 

Con solo l'operatore sopra definito, il compilatore genera un errore che la conversione non è disponibile se si tenta il seguente: 2 == a (considerando che la classe A non ha costruttori impliciti che prendono un intero come argomento)

Per ogni operazione binaria, il compilatore tenta di eseguire una conversione implicita per adattare l'operazione. Ad esempio, se class A avesse una definizione operator int, non sarebbero necessari gli operatori, poiché il compilatore converte implicitamente il tipo A in un numero intero e quindi esegue l'operazione bool operator==(int,int). Se nessun operatore è definito, il compilatore genera un errore, dicendo che non è disponibile alcuna conversione (cioè nessun operatore == che accetta A come argomento sul lato sinistro o destro)

Problemi correlati