2010-04-23 30 views
5

¿Es posible en tiempo de ejecución para crear una clase de DataTable donde ColumnName será propiedades de clase dinámica?creación Clase dinámica en C#

+0

¿Por qué? ¿Que estás tratando de hacer? – SLaks

+0

¿Quiere decir definir una nueva clase o establecer dinámicamente las propiedades de una clase existente? – JustLoren

+0

Quiero crear una nueva clase con los nombres de columna de dataTable – Polaris

Respuesta

1

Sí (usando Reflection.Emit), pero es una mala idea.
¿Qué estás tratando de hacer?

+0

Tengo RadGridView que tiene algunos problemas cuando uso DataTable como fuente para él. Pero cuando uso List todo funciona bien. ¿Algunas ideas? – Polaris

+1

Debe preguntar eso como una pregunta separada. – SLaks

1

leer sus comentarios, me undestood su media. Simplemente use Generics: usando los campos de lista para generar los objetos. El código es bastante simple:

public class DynClass<T, P> 
    { 
     public DynClass() 
     { 
      _fields = new Dictionary<T, P>(); 
     } 

     private IDictionary<T, P> _fields; 

     public IDictionary<T, P> Fields 
     { 
      get { return _fields; } 
     } 

    } 

    public class TestGenericInstances 
    { 
     public TestGenericInstances() 
     { 
      Client cli = new Client("Ash", "99999999901"); 

      /* Here you can create any instances of the Class. 
      * Also DynClass<string, object> 
      * */ 
      DynClass<string, Client> gen = new DynClass<string, Client>(); 

      /* Add the fields 
      * */ 
      gen.Fields.Add("clientName", cli); 

      /* Add the objects to the List 
      * */ 
      List<object> lstDyn = new List<object>().Add(gen); 
     }   
    } 
+0

Cada vez que puedo tener diferentes columnas con diferentes nombres y tipos. ¿Puede decirme sobre su variante en detalles o mostrarme una paz de código? – Polaris

1

Si tiene C# 4 se puede hacer uso de las nuevas dinámicas de la característica y el ExpandoObject. Puede read a tutorial about it here.

+2

¡Es realmente increíble lo que es posible con esta tecnología! – Erup

4

con C# 4, usted puede hacer esto

dynamic foo = new ExpandoObject(); 

// mimic grabbing a column name at runtime and adding it as a property 
((IDictionary<string, object>)foo).Add("Name", "Apple"); 

Console.WriteLine(foo.Name); // writes Apple to screen 

no recomendar ni nada, pero demuestra que es posible.

+0

gran herramienta pero no en mi caso. Yo uso framework 3.5 – Polaris

0

voy a estar buscando en el ExpandoObject que se ha mencionado (I votó por esa solución, por cierto, ya que parece más fácil) pero sí, es posible. Estoy construyendo una clase en uno de mis proyectos donde una utilidad de terceros requiere una línea CSV para ser definida como una clase.

Usted puede construir el código (que incluyen \ r \ n para que pudiera leer el código resultante):

 string code = "using FileHelpers;\r\n\r\n"; 

     code += "[DelimitedRecord(\"" + delimiter + "\")]\r\n"; 
     code += "public class CustomCSVInputFile "; 
     code += "{ \r\n"; 

     foreach (string column in columnList) 
     { 
      code += " public string " + column.Replace(" ", "") + ";\r\n"; 
     } 
     code += "}\r\n"; 

     CompilerResults compilerResults = CompileScript(code); 

...

public static CompilerResults CompileScript(string source) 
    { 
     CompilerParameters parms = new CompilerParameters(); 
     FileHelperEngine engine; 

     parms.GenerateExecutable = false; 
     parms.GenerateInMemory = true; 
     parms.IncludeDebugInformation = false; 

     string path = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().GetName().CodeBase).Replace("file:\\", "").Trim(); 

     parms.ReferencedAssemblies.Add(Path.Combine(path, "FileHelpers.dll")); 

     CodeDomProvider compiler = CSharpCodeProvider.CreateProvider("CSharp"); 

     return compiler.CompileAssemblyFromSource(parms, source); 
    } 

... Como he mencionado Si tuviera que hacerlo de nuevo, investigaría el ExpandoObject, pero definitivamente es posible crear una clase a partir de una DataTable. Necesitaría interrogar los nombres de las columnas para construir sus campos; mi ejemplo tenía la lista de nombres de columna proporcionados desde una cadena delimitada ",".

Mi ejemplo es de un caso de uso muy específico, pero debería ser suficiente para que te vas si el ExpandoObject no funcionar para usted.