2010-09-18 14 views
80

En C# 3.0 puede crear clase anónima con la siguiente sintaxis¿Cómo nueva clase anónima dinámica?

var o1 = new { Id = 1, Name = "Foo" }; 

¿Hay una manera de crear estos dinámico clase anónima a una variable?


Ejemplo:

var o1 = new { Id = 1, Name = "Foo" }; 
var o2 = new { SQ = 2, Birth = DateTime.Now }; 

dinámico crear Ejemplo:

var o1 = DynamicNewAnonymous(new NameValuePair("Id", 1), new NameValuePair("Name", "Foo")); 
var o2 = DynamicNewAnonymous(new NameValuePair("SQ", 2), new NameValuePair("Birth", 
DateTime.Now)); 

Beacuse que tengo que hacer:

dynamic o1 = new ExpandObject(); 
o1."ID" = 1; <--"ID" is dynamic name 
o1."Name" = "Foo"; <--"Name" is dynamic name 

Y Escena1:

void ShowPropertiesValue(object o) 
{ 
    Type oType = o.GetType(); 
    foreach(var pi in oType.GetProperties()) 
    { 
    Console.WriteLine("{0}={1}", pi.Name, pi.GetValue(o, null)); 
    } 
} 

si llamo:

dynamic o1 = new ExpandObject(); 
o1.Name = "123"; 
ShowPropertiesValue(o1); 

No se puede mostrar el resultado:

Name = 123 

Y también cómo convertir la ExpandoObject a AnonymouseType?

Type type = o1.GetType(); 
type.GetProperties(); <--I hope it can get all property of o1 

pasado, modifico método ShowPropertiesValue()

void ShowPropertiesValue(object o) 
{ 
    if(o is static object) <--How to check it is dynamic or static object? 
    { 
    Type oType = o.GetType(); 
    foreach(var pi in oType.GetProperties()) 
    { 
     Console.WriteLine("{0}={1}", pi.Name, pi.GetValue(o, null)); 
    } 
    } 
    else if(o is dynamic object) <--How to check it is dynamic or static object? 
    { 
    foreach(var pi in ???) <--How to get common dynamic object's properties info ? 
    { 
     Console.WriteLine("{0}={1}", pi.Name, pi.GetValue(o, null)); 
    } 
    } 
} 

cómo poner en práctica el método DynamicNewAnonymous o cómo modificar el ShowPropertiesValue()?

Mis motivaciones es:

dynamic o1 = new MyDynamic(); 
o1.Name = "abc"; 
Type o1Type = o1.GetType(); 
var props = o1Type.GetProperties(); <--I hope can get the Name Property 

Si puedo enganchar Método GetType de dynamicObject, y obligar a convertir Tipo-inflexible de tipos. El código transparente anterior puede funcionar bien.

+0

@Vlad: Admito que no estoy nada claro sobre las motivaciones. –

+0

@VladLazarenko Creo que tienes razón :-) – oberfreak

+0

Cuéntanos qué quieres hacer y por qué esta es tu solución seleccionada. – oberfreak

Respuesta

61

Los tipos anónimos son solo tipos regulares que se declaran implícitamente. Tienen poco que ver con dynamic.

Ahora, si usara un ExpandoObject y lo referenciara a través de una variable dynamic, podría agregar o eliminar campos sobre la marcha.

edición

Claro que se puede: simplemente echarlo a IDictionary<string, object>. Entonces puedes usar el indexador.

se utiliza la misma técnica de fundición para iterar sobre los campos:

dynamic employee = new ExpandoObject(); 
employee.Name = "John Smith"; 
employee.Age = 33; 

foreach (var property in (IDictionary<string, object>)employee) 
{ 
    Console.WriteLine(property.Key + ": " + property.Value); 
} 
// This code example produces the following output: 
// Name: John Smith 
// Age: 33 

El código anterior y más se puede encontrar haciendo clic en ese enlace.

+1

Pero ExpandoObject no puede hacerlo: 'dynamic o1 = new ExpandObject(); o1. "ID" = 1; o1. "Nombre" = "Foo"; ' – Flash

+0

Pero tampoco puede hacer: Escriba o1Type = o1.GetType(); var props = o1Type.GetProperties(); props está vacío – Flash

+1

Todo lo que hace es decir que las propiedades dinámicas no son idénticas a las propiedades fuertemente tipadas. Esto es trivialmente cierto. –

5

Se puede crear un ExpandoObject así:

IDictionary<string,object> expando = new ExpandoObject(); 
expando["Name"] = value; 

Y después de la fundición en dinámico, esos valores se verá como propiedades:

dynamic d = expando; 
Console.WriteLine(d.Name); 

Sin embargo, no son propiedades reales y no pueden ser accedido usando Reflection. Así que la siguiente declaración devolverá un valor nulo:

d.GetType().GetProperty("Name")