2009-11-05 27 views
7

He creado dos enumeraciones y sé que no son las mismas pero aún así creo que tiene sentido que sean igual a ya que su representación de cadena, así como su representación numérica son iguales (e incluso las mismas ...)¿Cuándo dos enumeraciones son iguales en C#?

En otras palabras: me gustaría que la primera prueba pase y la segunda falle. En realidad, sin embargo, ambos fracasan. Entonces: ¿cuándo son iguales dos enums en C#? ¿O hay alguna forma de definir el operador de iguales en C#?

Gracias!

public enum enumA {one, two} 

    public enum enumB {one, two} 

    [Test] 
    public void PreTest() 
    {   
    Assert.AreEqual(enumA.one,enumB.one); 
    Assert.AreSame(enumA.one, enumB.one); 
    } 

ACTUALIZACIÓN: 1) Por lo tanto las respuestas hasta ahora todo se comparan las representaciones, ya sea ints o cuerdas. ¿Enum en sí siempre es desigual? ¿No hay forma de definir la igualdad para eso?

+0

Duplicado: http://stackoverflow.com/questions/1410131/comparing-two-enum-types-for-equivalence –

+0

@Robert: gracias por el enlace, interesante y relacionado. Claramente no duplicado: solicita el valor de una enumeración. – Peter

Respuesta

14

enumeraciones son fuertemente tipados en C#, por lo tanto, enumA.one != enumB.one. Ahora, si convirtieras cada enumeración a su valor entero, serían iguales.

Assert.AreEqual((int)enumA.one, (int)enumB.one); 

Además, me gustaría desafiar la afirmación de que debido a que tienen el mismo número entero o representación de cadena que deben ser los mismos o iguales. Dadas dos enumeraciones NetworkInterface y VehicleType, no sería lógico que C# o .Net Framework permitieran que NetworkInterface.None iguale a VehicleType.None cuando se compara como enumeración, ya sea por valor o por cadena. Sin embargo, si el desarrollador arroja la enumeración fuertemente tipada a un entero o cadena, no hay nada que el lenguaje o el marco pueda hacer para evitar que los dos sean iguales.

Para aclarar más, no puede anular MyEnum.Equals para proporcionar un método de igualdad diferente. . Las enumeraciones .Net no son del todo las de primera clase que son en las versiones posteriores de Java, y me gustaría que C# permitiera interacciones más ricas con Enums.

+1

tenga cuidado aquí, esto solo es cierto si la posición ordinal es la misma. –

+1

gracias. Pero el operador! = NO ES el que estoy después de más bien equals(). Incluso diferentes tipos fuertemente tipados pueden ser iguales, pensé, ¿o no es cierto? – Peter

+0

@ Peter: las enumeraciones son estructuras, además, no puede sobrecargar ninguno de sus métodos. También utilicé! = Como más de un verbo que como un fragmento de código real. @Tim: de hecho, esto es solo para su caso y su caso. – user7116

0
public enum enumA {one = 1, two = 2} 

    public enum enumB {one = 1, two = 2} 

    [Test] 
    public void PreTest() 
    {      
     Assert.AreEqual((int)enumA.one, (int)enumB.one); 
     // I don't think this one will ever pass 
     Assert.AreSame(enumA.one, enumB.one); 
    } 
1

Si usted quiere que coinciden, los fundió a int

Assert.AreEqual((int)enumA.one,(int)enumB.one); 

pasaría porque son los dos primeros figuran el. Si quieres que coincidan porque ambos dicen "uno", entonces necesitas usar el reflejo.

+2

Creo que puede hacer esto para verificar los valores de cadena: Assert.AreEqual (enumA.one.ToString(), enumB.one.ToString()); – Jonas

+0

o casting a la secuencia, por supuesto. – Peter

0

Usted podría intentar echarlos:

Assert.AreEqual((int)enumA.one, (int)enumB.one); 
1

Para ser honesto, la igualdad no es directa la mayor parte del tiempo.

Me inclino a crear una clase auxiliar que implemente IEqualityComparer (y cualquier otra prueba de igualdad, IsSame() por ejemplo) y la use.

3

Te hacen referencia a la versión 3.0 de C# Language Specification, de la que esta cita ha sido extraída de la sección de enumeración en la página 29:

"Cada tipo de enumeración tiene un tipo integral correspondiente llamado el tipo subyacente de la tipo enum. Un tipo enum que no declara explícitamente un tipo subyacente tiene un tipo subyacente de int. El tipo de enum y el rango de valores posibles de un tipo de enumeración están determinados por su tipo subyacente. El conjunto de valores que puede tomar un tipo enum es no limitado por sus miembros enum. En particular, cualquier valor del tipo subyacente de una enumeración se puede convertir al tipo de enumeración y es un valor válido distinto de ese tipo de enumeración."

El método .AreEqual está realmente poniendo a prueba la equivalencia mientras que la identidad segundas pruebas. Por lo tanto, sólo tiene que emitir cada uno a su tipo subyacente (en este caso, int) y luego hacer la comparación.

public enum enumA { one, two } 
public enum enumB { one, two } 
[Test] 
public void PreTest() 
{ 
     Assert.AreEqual((int)enumA.one,(int)enumB.one); 
     Assert.AreSame(enumA.one, enumB.one); 
} 
+0

Tx, ¿me puede dar un enlace? – Peter

2

diferencia Java, C# no proporciona ningún recurso para agregar métodos (como operador ==()) a una enumeración.

Lo que he hecho en el pasado cuando necesitaba enums más inteligentes es crear una clase XHelper (donde X es el nombre de la enumeración), y puse todos los métodos en él. Por lo tanto, algo como esto:

public static bool EnumAHelper.EqualsEnumB(EnumA enumA, EnumB enumB) 
{ 
    return (int)enumA == (int)enumB; 
} 

Sin embargo, no recuerdo haber encontrado un caso en el que necesitaba dos enumeraciones diferentes para significar lo mismo.

+0

Muy buena observación (después de todo). Estoy reescribiendo una clase existente que quiero que sea compatible, por lo que las enumeraciones deberían ser las mismas también. – Peter

Cuestiones relacionadas