2010-05-04 33 views
6

Sé que los genéricos están en C# para cumplir un rol similar a las plantillas C++, pero realmente necesito generar código en tiempo de compilación. En esta situación particular, sería muy fácil resolver el problema con plantillas C++ .Plantillas en C#

¿Alguien conoce alguna alternativa? ¿Quizás un complemento VS que preproceses el código o algo así? No necesita ser muy sofisticado, solo necesito generar algunos métodos en tiempo de compilación.

Aquí hay un ejemplo muy simplificado en C++ (tenga en cuenta que este método se llamaría dentro de un ciclo cerrado con varias condiciones en lugar de solo "Avanzado" y esas condiciones cambiarían solo una vez por fotograma, usando if sería demasiado lento y escribiría todos los métodos alternativos a mano serían imposibles de mantener). También tenga en cuenta que el rendimiento es muy importante y es por eso que necesito que esto se genere en tiempo de compilación.

template <bool Advanced> 
int TraceRay(Ray r) 
{ 
    do 
    { 
     if (WalkAndTestCollision(r)) 
     { 
      if (Advanced) 
       return AdvancedShade(collision); 
      else 
       return SimpleShade(collision); 
     } 
    } 
    while (InsideScene(r)); 
} 
+1

Por curiosidad, ¿puede proporcionar un ejemplo de código de la plantilla C++ que usaría? Puede haber un enfoque alternativo que pueda lograr lo que desea en C#. –

+0

Agregó un ejemplo simple. –

+0

Tenga en cuenta que C# usa un compilador JIT. Por lo tanto, incluso las sentencias "if" que se evalúan en "tiempo de ejecución" pueden optimizarse en código compilado por el JIT, siempre que pueda determinar que solo se tomará una ruta. Además, si te importa este nivel de rendimiento, no deberías usar código administrado en primer lugar. –

Respuesta

9

usted puede utilizar T4.

EDIT: En su ejemplo, puede usar un parámetro simple bool.

+0

+1: Esta es probablemente la opción más rica en características presentada hasta ahora. (Aunque alguna explicación ayudaría también;)) –

+0

T4 parece hacer lo que quiero, ¡gracias! No es tan limpio como las plantillas de C++, pero es solo una clase de cuello de botella, así que probablemente lo haga. –

1

En realidad, hasta donde yo sé. Puede hacer este tipo de cosas en runtime, por supuesto; algunas opciones de programación meta, ninguno de ellos trivial:

  • reflexión (la opción más sencilla si no necesitan "más rápida posible")
  • CSharpCodeProvider y algunos de generación de código
  • lo mismo con CodeDom
  • ILGenerator si quieres incondicional
+0

También PostSharp (www.sharpcrafters.com) está en la misma categoría y podría ser utilizado. – cfeduke

+0

Lamentablemente, el rendimiento es esencial, por lo que debe generarse en tiempo de compilación. –

0

Los genéricos funcionan como plantillas, si ese es el caso. Hay una manera de crear código en tiempo de ejecución -

Check es CodeProject Ejemplo:

CodeProject

+0

Quiere hacer esto en tiempo de compilación. – SLaks

0

Además de excelentes sugerencias de Marc, es posible que desee echar un vistazo a PostSharp.

0

He hecho algunos trucos de metaprogramación usando genéricos estáticos que usan reflexión (y ahora estoy usando generación de código dinámico usando System.Linq.Expressions, y también he usado ILGenerator para cosas más locas). http://www.lordzoltan.org/blog/post/Pseudo-Template-Meta-Programming-in-C-Sharp-Part-2.aspx para un ejemplo que armé (disculpe la falta de formato del código, ¡es una publicación muy antigua!) Que podría ser útil.

También he usado T4 (el enlace va a una serie de tutoriales de mi autoridad favorita en T4 - Oleg Sych), como lo sugiere SLaks, que es una manera muy buena de generar código, especialmente si también cómodo con la sintaxis del estilo Asp.Net Si genera clases parciales utilizando la salida T4, entonces el desarrollador puede embellecer y agregar a la clase como mejor le parezca.

Si tiene que ser absolutamente tiempo de compilación, entonces elegiría T4 (o escribiría su propia herramienta personalizada, pero eso es un poco pesado). De lo contrario, un genérico estático podría ayudar, probablemente en asociación con el tipo de soluciones mencionadas por Marc.

0

Si desea la generación de código verdadero, puede usar CodeSmith http://www.codesmithtools.com que no es gratuito/incluido como T4, pero tiene algunas características más y puede funcionar como un complemento de VS.NET.

0

He aquí un artículo antiguo que utiliza programación genética para generar y compilar el código sobre la marcha:

http://msdn.microsoft.com/en-us/magazine/cc163934.aspx

"La clase Generator es el núcleo de la aplicación de la programación genética Se descubre terminales y la clase base disponibles. funciones. Genera, compila y ejecuta el código C# para buscar una buena solución al problema que se le da. El constructor recibe un tipo de sistema que es la clase raíz para las operaciones de reflexión .NET.

Puede ser exagerado para su situación, pero muestra lo que C# puede hacer. (Tenga en cuenta que este artículo es de 1.0 días)