Tengo dos objetos en C # y no sé si es booleano o de cualquier otro tipo. Sin embargo, cuando trato de comparar esos C # no puede dar la respuesta correcta. He intentado el mismo código con VB.NET y ¡lo hice!
¿Alguien puede decirme cómo solucionar esto si hay una solución?
C#:
object a = true;
object b = true;
object c = false;
if (a == b) c = true;
MessageBox.Show(c.ToString()); //Outputs False !!
VB.NET:
Dim a As Object = True
Dim b As Object = True
Dim c As Object = False
If (a = b) Then c = True
MessageBox.Show(c.ToString()) '// Outputs True
c#
.net
vb.net
comparison
Mohsen Sarkar
fuente
fuente
a.Equals(b)
?a
, obtiene boxeo y crea un cuadro que contienetrue
. Cuando lo asignab
, obtiene otro cuadro que también contienetrue
. Cuando comparaa
yb
, dado que ambos son del tipo de tiempo de compilaciónobject
, llama a la sobrecargaoperator ==(object, object)
definida por la Especificación del lenguaje C #. Esta sobrecarga verifica si las referencias van al mismo objeto. Como tiene dos cuadros, el resultado esfalse
, y la declaración "debajo"if
no se ejecutará. Para comprender esto mejor, intente cambiar la asignación deb
a esto:object b = a;
ahora solo tiene una casilla.Respuestas:
En C #, el
==
operador (cuando se aplica a expresiones de tipo de referencia) realiza una verificación de igualdad de referencia a menos que esté sobrecargado . Estás comparando dos referencias que son el resultado de conversiones de boxeo, por lo que esas son referencias distintas.EDITAR: con tipos que sobrecargan
==
, puede obtener un comportamiento diferente, pero eso se basa en el tipo de tiempo de compilación de las expresiones. Por ejemplo,string
proporciona==(string, string
):Aquí, la primera comparación usa el operador sobrecargado, pero la segunda usa la comparación de referencia "predeterminada".
En VB, el
=
operador hace mucho más trabajo: ni siquiera es equivalente al usoobject.Equals(x, y)
, ya que cosas comoOption Compare
pueden afectar la forma en que se compara el texto.Básicamente, los operadores no funcionan de la misma manera y no están destinados a funcionar de la misma manera.
fuente
=
hizo en VB, pero la especificación no es muy clara.bool == bool
comparación.Además de la respuesta de Jon que explica el lado C # de las cosas, esto es lo que hace VB:
En VB con
Option Strict On
, una comparación a través de=
siempre prueba la igualdad de valores y nunca la igualdad de referencia. De hecho, su código ni siquiera se compila una vez que cambiaOption Strict On
porqueSystem.Object
no define unOperator=
. Usted debe siempre tener esta opción, atrapa insectos con más eficacia que una venus atrapamoscas (aunque en su caso particular, este comportamiento laxa en realidad hace lo correcto). 1De hecho, con
Option Strict On
, VB se comporta aún más estricto que C #: en C #,a == b
ya sea activa una llamada aSomeType.operator==(a, b)
o, si esto no existe, invoca comparación de igualdad de referencia (que es equivalente a llamarobject.ReferenceEquals(a, b)
).En VB, por otro lado, la comparación
a = b
siempre invoca al operador de igualdad. 2 Si desea utilizar la comparación de igualdad de referencia, debe utilizarlaa Is b
(que, una vez más, es lo mismo queObject.ReferenceEquals(a, b)
)1) Aquí hay una buena indicación de por qué usar
Option Strict Off
es una mala idea: he usado VB.NET durante casi una década, desde antes del lanzamiento oficial de .NET hasta hace unos años, y no tengo ni idea de quéa = b
haceOption Strict Off
. Hace algún tipo de comparación de igualdad, pero qué sucede exactamente y por qué, ni idea. Sindynamic
embargo, es más complejo que la función de C # (porque se basa en una API bien documentada). Esto es lo que dice el MSDN:2) Jon ha mencionado una excepción, cadenas, donde la comparación de igualdad hace algunas cosas más por razones de compatibilidad con versiones anteriores.
fuente
Option Strict On
tiene que ser considerado un delito penal ...Las instancias de objeto no se comparan con el operador "==". Debe usar el método "igual". Con el operador "==" se comparan referencias, no objetos.
Prueba esto:
Resultados:
Ahora, intenta esto:
Resultados:
fuente
operator ==
. Si anula ese operador y no es igual, su salida se revertirá. No hay nada inherente en comparar referenciasoperator ==
ni nada inherente en comparar valores enEquals
. Son solo dos formas de determinar la igualdad; ambos tienen implementaciones predeterminadas de una comparación de referencia, y ambos pueden anularse para hacer lo que usted quiera que hagan. La única otra diferencia es queEquals
es virtual yoperator ==
no lo es.==
, solo puede sobrecargarlo .El problema es que el operador == en C # es una llamada a un método estático (bueno, tal vez no técnicamente, pero puede considerarse como tal) según el tipo de tiempo de compilación de los dos parámetros. Los tipos de tiempo de ejecución reales de esos objetos no importan.
Basado en ese tipo de tiempo de compilación, el compilador determinará qué implementación
operator ==
usar. Puede usar el predeterminadoobject
implementación , podría usar una de las sobrecargas numéricas proporcionadas por el lenguaje, o podría ser una implementación definida por el usuario.Esto es diferente de VB en que VB no determina la implementación en tiempo de compilación. Espera hasta el tiempo de ejecución e inspecciona los dos parámetros que se le dan para determinar qué implementación del
==
operador debe usar.Su código contiene valores booleanos, pero están en variables que son de tipo
object
. Porque la variable es de tipoobject
, el compilador de C # usa laobject
implementación de==
, que compara las referencias , no las instancias de objeto. Como los valores booleanos son cuadros, no tienen la misma referencia, aunque sus valores sean los mismos.Al código VB no le importa de qué tipo es la variable. Espera hasta el tiempo de ejecución y luego verifica las dos variables, ve que en realidad son del tipo booleano y, por lo tanto, usa la
==
implementación del operador booleano . Esa implementación compara los valores de los booleanos, no sus referencias (y los booleanos se desempaquetarán antes de llamar a ese operador, por lo que una comparación de referencia ya no tiene sentido). Debido a que los valores de los booleanos son los mismos, devuelve verdadero.fuente
=
hace exactamente en VB para decirlo con certeza.=
, junto con todos los otros operadores de comparación relacionales, tales como<
,>=
, etc. , reciben un tratamiento especial cuando ambos o cualquier lado del operador lo estáObject
. Este tratamiento especial se realiza para que los programadores de VB6, que están acostumbrados a usar un tipo conocido comoVariant
en VB pre.NET, puedan usarloObject
en VB.Net de la forma en que lo han hechoVariant
antes.Option Strict On
, VB=
está predispuesto a desempaquetar unObject
hasta que pueda llegar a un String o numérico.