2009-08-09 17 views
13

Como operadores C# p. +, + =, == son invalidables. Me permite pensar que son una especie de métodos, por lo tanto, me pregunto si hay una manera de llamarlos usando la reflexión, en Int32, por ejemplo.¿Es posible llamar operadores de tipo de valor a través de la reflexión?

+6

Los operadores no pueden * anular *. Pueden estar * sobrecargados *. Hay una gran diferencia. –

+1

Para ser más claro, la anulación le permite redefinir la implementación, la sobrecarga le permite agregar otro método con el mismo nombre pero con diferentes parámetros. Gracias por el comentario. –

+0

Respondió para comentar y agregó un ejemplo no tipado. –

Respuesta

7

Sí, los operadores personalizados son invocables mediante la reflexión (tienen nombres especiales, como op_Addition), pero System.Int32 no los define, ya que los tipos fundamentales, integrados, se manejan directamente mediante códigos de operación IL como add , en lugar de llamadas a métodos.

+1

¿qué son los operadores de molde personalizados nombrados? –

+1

Contestación propia de respuesta: resulta que son "op_Implicit" y "op_Explicit" y pueden tener varias versiones con el mismo nombre, que difieren solo en el tipo de devolución. –

0

Sería muy ineficiente si agregar o comparar dos enteros requiriera una llamada a un método para que estas simples operaciones sobre los tipos fundamentales sean generadas por código como se explica en otra respuesta y no se pueda invocar utilizando la reflexión. Un interesante tipo de valor incorporado es decimal (o System.Decimal). Este struct tiene soporte para valores literales en C#, pero se comporta como un tipo de valor real real y expone una gran cantidad de operadores que se pueden invocar a través de la reflexión.

Si tiene curiosidad puede usar Reflector para buscar a todos los miembros expuestos por System.Int32.

0

Existen buenas respuestas aquí, por lo que acaba de añadir algo aún no he mencionado:

una estructura podría tener un operator overloaded. Esto significa más opciones para verificar si intenta crear algún enfoque programático.

Una cosa agradable de probar es probar el enfoque del árbol de expresiones. Here es una pequeña muestra. Por supuesto, el rendimiento no es muy bueno, pero de todos modos sabemos en qué nos estamos metiendo con Reflection.

4

¿Qué es exactamente lo que quieres hacer? Tratar con los diversos significados de los operadores (primitivo (asignado a instrucciones específicas de IL), personalizado (asignado a métodos estáticos) y elevado (proporcionado como un patrón por el compilador) hace que esto sea doloroso. Si solo desea use los operadores, entonces es posible escribir código que brinde soporte al operador a través de genéricos. Tengo un código para esto que está disponible gratuitamente en MiscUtil (description and examples).


A modo de ejemplo sin tipo (una nota que esto no es enormemente eficiente, pero funciona):

object x = 123, y = 345; // now forget that we know that these are ints... 
object result = Expression.Lambda<Func<object>>(
    Expression.Convert(Expression.Add(
     Expression.Constant(x), Expression.Constant(y)), 
    typeof(object))).Compile()(); 
+0

En realidad, quería implementar un Add (objeto a la izquierda, objeto a la derecha) donde el valor devuelto usa el tipo del argumento de la izquierda. Esto es para una evaluación de expresión, y como es dinámica, no hay forma de escribir el código directamente. –

+1

En ese caso, te encantará 'dynamic' en 4.0; hará más o menos esto ... –

+0

tiene que estar en desacuerdo al optar por 4.0 ya que el trabajo de Seb se centra y es un gran logro cuando se compara con la hinchazón y la invención de Expression Trees. A juzgar por el rendimiento de DLR y sus bits de contención, solo hace que la inminente liberación de PDC sea el marco más lento en la historia de la humanidad. –

8

¿Qué hay de esto, es simple, pequeño y funciona :)

public T Add<T>(object x, object y) 
{ 
    return (T)Convert.ChangeType((dynamic)x + (dynamic)y, typeof(T)); 
} 
+0

Esto funcionó maravillosamente en mi aplicación. La primera vez que he usado realmente "dinámico" también. ¡Me gusta! – Boinst

Cuestiones relacionadas