español - return enum c#
C#7.3 Restricción de enumeración: ¿Por qué no puedo usar la palabra clave enum? (1)
Para restringir un parámetro de tipo genérico para que sea de un tipo de enumeración, anteriormente los restringí de esta manera, que era lo mejor que podía hacer para restringir el tipo T para las enumeraciones en pre-C # 7.3:
void DoSomething<T>() where T : struct, IComparable, IConvertible, IFormattable
Ahora, C # 7.3 agrega una nueva característica para restringir un tipo genérico a System.Enum
. Intenté usar la restricción de enumeración con la actualización VS2017 15.7 lanzada hoy , y se compila correctamente cuando la escribo de esta manera (dado que tengo una directiva using System;
):
void DoSomething<T>() where T : Enum
Sin embargo, el uso de la palabra clave enum
no funciona y hace que el compilador arroje los siguientes errores (hay más errores a continuación, se espera un cuerpo del método, pero realmente no vale la pena mencionarlo aquí, supongo):
void DoSomething<T>() where T : enum
^ error CS1031: Type expected
error CS1002: ; expected
^ error CS1001: Identifier expected
error CS1514: { expected
error CS1513: } expected
Dado que hay una restricción de struct
que funciona para las estructuras, no entiendo por qué la enum
no funciona aquí para las enumeraciones. Es cierto que la enum
no se asigna a un tipo real como lo haría int
para Int32
, pero pensé que debería comportarse de la misma manera que la restricción de struct
.
¿Acabo de caer en una trampa de características experimentales que aún no se ha implementado completamente, o fue hecho a propósito en la especificación (por qué)?
La restricción de struct
en los genéricos no se asigna a un tipo real (aunque podría, en teoría, ValueType
a ValueType
). De manera similar, la enum
no se asigna limpiamente a los tipos reales de la misma manera que la string
, int
o long
, establece una sintaxis especial para crear una clase de constantes simbólicas que se asignan a valores enteros; por lo tanto, public enum Stuff
lugar de public class Stuff : Enum
. Tenga en cuenta que si esto último se hubiera implementado en su lugar, sería más sutil, ya que cambiaría la sintaxis en función del tipo heredado, en lugar de cambiar la sintaxis en función de una palabra clave que no sea de class
.
Entonces, en conclusión, sí, where T : enum
no está destinado a funcionar porque enum
es una palabra clave, no un alias de tipo. Si realmente quieres verlo funcionar porque enum
al menos huele como un alias de tipo en contexto como estos, ¡pídelo!
EDITAR: Para alguna referencia histórica, aquí hay una pregunta de 2008 que indica que Enum
no era una restricción válida, ya que es una clase especial.