Skip to content

Instantly share code, notes, and snippets.

@Fhernd
Created June 13, 2014 16:23
Show Gist options
  • Save Fhernd/33fd1ff9371cd45378ee to your computer and use it in GitHub Desktop.
Save Fhernd/33fd1ff9371cd45378ee to your computer and use it in GitHub Desktop.
Demostración de herencia de DynamicObject para la creación de un tipo dinámico con miembros de esta misma naturaleza en C#.
using System;
using System.Collections.Generic;
using System.Dynamic;
namespace Recetas.Cap03
{
public class ClaseDinamica : DynamicObject
{
// Diccionario con los miembros (e.g., propiedades) agregadas
// y consultadas de manera dinámica:
private Dictionary<string, object> miembros = new Dictionary<string, object>();
///<summary>
/// Retorna el valor del miembro invocado.
///</summary>
///<param name="binder">Información del objeto que invocó la operación dinámica.</param>
///<param name="resultado">Resultado de la operación.</param>
///<returns>true si el miembro existe. false, en caso contrario.</returns>
public override bool TryGetMember(GetMemberBinder binder, out object resultado)
{
if (miembros.ContainsKey (binder.Name))
{
resultado = miembros[binder.Name];
return true;
}
else
{
return base.TryGetMember(binder, out resultado);
}
}
///<summary>
/// Establece el valor al miembro invocado.
///</summary>
///<param value="binder">Información del objeto que invocó la operación dinámica.</param>
///<param value="valor">Valor a establecer sobre el miembro.</param>
///<returns>true.</returns>
public override bool TrySetMember(SetMemberBinder binder, object valor)
{
// Si no contiene la propiedad, la crea (agrega):
if (!miembros.ContainsKey (binder.Name))
{
miembros.Add (binder.Name, valor);
}
else
{
miembros[binder.Name] = valor;
}
return true;
}
///<summary>
/// Invoca un miembro.
///</summary>
///<param value="binder">Información acerca de la operación dinámica.</param>
///<param value="args">Argumentos del objeto que invoca la operación dinámica.</param>
///<param value="resultado">Resultado de la invocación del miembro.</param>
///<returns>true.</returns>
public override bool TryInvokeMember (InvokeMemberBinder binder, object[] args, out object resultado)
{
if (miembros.ContainsKey (binder.Name) && miembros[binder.Name] is Delegate)
{
resultado = (miembros[binder.Name] as Delegate).DynamicInvoke(args);
return true;
}
else
{
return base.TryInvokeMember(binder, args, out resultado);
}
}
///<summary>
/// Retorna los miembros de esta clase dinámica.
///</summary>
///<returns>Instancia IEnumerable<string> con los miembros de esta clase dinámica.</returns>
public override IEnumerable<string> GetDynamicMemberNames()
{
return miembros.Keys;
}
public static void Main()
{
// Declaramos un variable de tipo DynamicObject:
dynamic dyn;
// Encapsulamos una instancia de `ClaseDinamica`:
dyn = new ClaseDinamica();
// Creamos una propiedad de forma dinámica. La
// propiedad `Contador` con el valor 10:
dyn.Contador = 13;
// Creamos un delegado con una expresión lambda:
var delegadoConAction = new Action<string>(texto => Console.WriteLine (texto));
// Asignamos este delegado como miembro de la instancia de `ClaseDinamica`:
dyn.EscribirEnConsola = delegadoConAction;
// Invocamos el delegado y le pasamos como argumento de la
// propiedad dinámica `Contador`:
dyn.EscribirEnConsola (dyn.Contador.ToString());
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment