2009-04-09 27 views
5

La salida del código de abajo es la siguiente:== operador de sobrecarga cuando el objeto es en caja

no igual
igual

Nota la diferencia en el tipo de X y XX y que = = la sobrecarga del operador solo se ejecuta en el segundo caso y no en el primero.

¿Hay alguna manera de sobrecargar el operador == para que se ejecute siempre cuando se realiza una comparación entre las instancias de MyDataObejct?

Edit 1: # aquí quiero anular el operador == en MyDataClass, no estoy seguro de cómo puedo hacerlo para que case1 también ejecute la implementación sobrecargada ==.

class Program { 
    static void Main(string[] args) { 
     // CASE 1 
     Object x = new MyDataClass(); 
     Object y = new MyDataClass(); 
     if (x == y) { 
      Console.WriteLine("equal"); 
     } else { 
      Console.WriteLine("not equal"); 
     } 

     // CASE 2 
     MyDataClass xx = new MyDataClass(); 
     MyDataClass yy = new MyDataClass(); 
     if (xx == yy) { 
      Console.WriteLine("equal"); 
     } else { 
      Console.WriteLine("not equal"); 
     } 
    } 
} 

public class MyDataClass { 
    private int x = 5; 

    public static bool operator ==(MyDataClass a, MyDataClass b) { 
     return a.x == b.x; 
    } 

    public static bool operator !=(MyDataClass a, MyDataClass b) { 
     return !(a == b); 
    } 
} 

Respuesta

5

No, básicamente. == usa análisis estático, por lo que usará el objeto ==. Parece que necesita usar object.Equals(x,y) en su lugar (o x.Equals(y) si sabe que ninguno de los dos es nulo), que usa polimorfismo.

+1

Como punto de interés, ¿cuál es el razonamiento para no tener operadores polimórficos? Me parece que el polimorfismo sería más intuitivo. – Welbog

+0

, pero ¿cuál ganaría? en a == b, ¿qué método se llama? especialmente si a/b son subtipos diferentes ... –

+1

Además, el polimorfismo dificultaría el uso de nulos en los operadores. –

1

Aquí es una descripción de cómo reemplazar los iguales y el operador ==:

http://msdn.microsoft.com/en-us/library/ms173147(VS.80).aspx

Esto es cómo se ve (a condición de que ya ha realizado una sobrecarga de Iguales()):

public static bool operator ==(MyDataClass a, MyDataClass b) 
{ 
    // If both are null, or both are same instance, return true. 
    if (System.Object.ReferenceEquals(a, b)) 
    { 
     return true; 
    } 

    // If one is null, but not both, return false. 
    if (((object)a == null) || ((object)b == null)) 
    { 
     return false; 
    } 

    // Otherwise use equals 
    return a.Equals(b); 
} 

public override bool Equals(System.Object obj) 
{ 
    // If parameter is null return false. 
    if (obj == null) 
    { 
     return false; 
    } 

    // If parameter cannot be cast to MyDataClass return false. 
    MyDataClass p = obj as MyDataClass; 
    if ((System.Object)p == null) 
    { 
     return false; 
    } 

    return (x == p.x); 
} 
+0

Probar 'b' for' null' en 'operator ==' no es necesario: esto ya está hecho en 'Equals'. Puede simplemente (implícitamente) delegar la prueba. Además, ¿por qué mezclar 'object.ReferenceEquals (x, y)' con '(object) x == (object) y'? Mantente constante. –