2010-03-04 12 views
5

En C# 4.0, hay un nuevo DynamicObject.C# 4.0 - ¿Llamar a un método protegido en un objeto dinámico llama a TryInvokeMember()?

Proporciona un "método mágico" TryInvokeMember() que se llama cuando se intenta llamar a un método que no existe.

http://msdn.microsoft.com/en-us/library/system.dynamic.dynamicobject.tryinvokemember%28VS.100%29.aspx

Lo que me gustaría saber es si TryInvokeMember() se llama cuando se trata de llamar a un método protegido desde fuera de la clase de definición.

Estoy contrastando el comportamiento con PHP, que llama a su "método mágico" __call() equivalente en esta situación.

+6

No es un problema, pero lo primero que haría en este escenario es probarlo y ver :) – spronkey

Respuesta

6

Cuando escribe una llamada que invoca un método que no es accesible (usando las reglas de acceso estándar de C#), entonces no se llamará al método inaccesible y el tiempo de ejecución llamará al TryInvokeMember (donde puede manejar la llamada de alguna otra manera). Este es un ejemplo, para que pueda probarlo:

class Test : DynamicObject { 
    public void Foo() { 
    Console.WriteLine("Foo called"); 
    } 
    protected void Bar() { 
    Console.WriteLine("Bar called"); 
    } 

    public override bool TryInvokeMember 
     (InvokeMemberBinder binder, object[] args, out object result) { 
    Console.WriteLine("Calling: " + binder.Name); 
    return base.TryInvokeMember(binder, args, out result); 
    } 
} 

Ahora, podemos crear una instancia del objeto y tratar de llamar a algunos de sus métodos:

dynamic d = new Test(); 
d.Foo(); // this will call 'Foo' directly (without calling 'TryInvokeMember') 
d.Bar(); // this will call 'TryInvokeMember' and then throw exception 

lo tanto, si se llama a la base implementación de TryInvokeMember, la carpeta dinámica C# fallará al llamar a un método inaccesible, pero puede definir su propio manejo de la caja en TryInvokeMember (estableciendo result en algún valor y devolviendo true).

+1

Solo para aclarar el problema. Lanza una excepción porque llama a una carpeta predeterminada. Simplemente cambie "return base.TryInvoke" a algo como "result = null; return true;" para evitar la excepción Probablemente no quiso decirlo, pero ahora parece que llamar a un método protegido siempre dará como resultado una excepción (¿o es mi escritor de tecnología el que pilla?) –

+0

Tomas, ha pasado mucho tiempo desde que dijiste que aclararías el última frase. ¿Cuánto tiempo deberíamos esperar? – KMX

Cuestiones relacionadas