simple - ¿Cómo convierto una enumeración a una lista en C#?
listas c++ insertar (14)
Esta pregunta ya tiene una respuesta aquí:
- ¿Cómo enumero una enumeración en C #? 26 respuestas
¿Hay alguna forma de convertir una enum
a una lista que contenga todas las opciones de la enumeración?
Aquí para su utilidad ... algo de código para obtener los valores en una lista, que convierte la enumeración en una forma legible para el texto
public class KeyValuePair
{
public string Key { get; set; }
public string Name { get; set; }
public int Value { get; set; }
public static List<KeyValuePair> ListFrom<T>()
{
var array = (T[])(Enum.GetValues(typeof(T)).Cast<T>());
return array
.Select(a => new KeyValuePair
{
Key = a.ToString(),
Name = a.ToString().SplitCapitalizedWords(),
Value = Convert.ToInt32(a)
})
.OrderBy(kvp => kvp.Name)
.ToList();
}
}
.. y el método de extensión System.String de soporte:
/// <summary>
/// Split a string on each occurrence of a capital (assumed to be a word)
/// e.g. MyBigToe returns "My Big Toe"
/// </summary>
public static string SplitCapitalizedWords(this string source)
{
if (String.IsNullOrEmpty(source)) return String.Empty;
var newText = new StringBuilder(source.Length * 2);
newText.Append(source[0]);
for (int i = 1; i < source.Length; i++)
{
if (char.IsUpper(source[i]))
newText.Append('' '');
newText.Append(source[i]);
}
return newText.ToString();
}
Esta es la manera que amo, usando LINQ:
public class EnumModel
{
public int Value { get; set; }
public string Name { get; set; }
}
public enum MyEnum
{
Name1=1,
Name2=2,
Name3=3
}
public class Test
{
List<EnumModel> enums = ((MyEnum[])Enum.GetValues(typeof(MyEnum))).Select(c => new EnumModel() { Value = (int)c, Name = c.ToString() }).ToList();
}
Espero eso ayude
Esto devolverá un IEnumerable<SomeEnum>
de todos los valores de un Enum.
Enum.GetValues(typeof(SomeEnum)).Cast<SomeEnum>();
Si desea que sea una List<SomeEnum>
, simplemente agregue .ToList()
después de .Cast<SomeEnum>()
.
Para usar la función Cast en una matriz, debe tener System.Linq
en su sección de uso.
La respuesta corta es, usar:
(SomeEnum[])Enum.GetValues(typeof(SomeEnum))
Si necesita eso para una variable local, es var allSomeEnumValues = (SomeEnum[])Enum.GetValues(typeof(SomeEnum));
.
¿Por qué la sintaxis es así?
El método static
GetValues
se introdujo en el antiguo .NET 1.0 días. Devuelve una matriz unidimensional del tipo de ejecución SomeEnum[]
. Pero como es un método no genérico (los genéricos no se introdujeron hasta .NET 2.0), no puede declarar su tipo de retorno (tipo de retorno en tiempo de compilación) como tal.
Las matrices .NET tienen un tipo de covarianza, pero como SomeEnum
será un tipo de valor y porque la covarianza de tipo de matriz no funciona con tipos de valor, ni siquiera pudieron declarar el tipo de devolución como un object[]
o Enum[]
. (Esto es diferente de, por ejemplo, esta sobrecarga de GetCustomAttributes
de .NET 1.0 que tiene un object[]
tipo de retorno de tiempo de compilación object[]
pero en realidad devuelve una matriz del tipo SomeAttribute[]
donde SomeAttribute
es necesariamente un tipo de referencia).
Debido a esto, el método .NET 1.0 tuvo que declarar su tipo de devolución como System.Array
. Pero te garantizo que es un SomeEnum[]
.
Cada vez que vuelva a llamar a GetValues
con el mismo tipo de enumeración, tendrá que asignar una nueva matriz y copiar los valores en la nueva matriz. Esto se debe a que los arreglos pueden ser escritos (modificados) por el "consumidor" del método, por lo que tienen que crear una nueva matriz para asegurarse de que los valores no se modifiquen. .NET 1.0 no tenía buenas colecciones de solo lectura.
Si necesita la lista de todos los valores en muchos lugares diferentes, considere llamar a GetValues
solo una vez y almacenar en caché el resultado en un contenedor de solo lectura, por ejemplo, como este:
public static readonly ReadOnlyCollection<SomeEnum> AllSomeEnumValues
= Array.AsReadOnly((SomeEnum[])Enum.GetValues(typeof(SomeEnum)));
Luego puede usar AllSomeEnumValues
muchas veces, y la misma colección se puede reutilizar de forma segura.
¿Por qué es malo usar .Cast<SomeEnum>()
?
Muchas otras respuestas utilizan .Cast<SomeEnum>()
. El problema con esto es que utiliza la implementación no genérica IEnumerable
de la clase Array
. Esto debería haber involucrado el recuadro de cada uno de los valores en un cuadro de System.Object
, y luego usar el método Cast<>
para desempaquetar todos esos valores nuevamente. Afortunadamente, el método .Cast<>
parece verificar el tipo de tiempo de ejecución de su parámetro IEnumerable
( this
parámetro) antes de que comience a iterar a través de la colección, por lo que no es tan malo después de todo. Resulta que .Cast<>
deja pasar la misma instancia de matriz.
Si lo sigues por .ToArray()
o .ToList()
, como en:
Enum.GetValues(typeof(SomeEnum)).Cast<SomeEnum>().ToList() // DON''T do this
tiene otro problema: crea una nueva colección (matriz) cuando llama a GetValues
y luego crea una nueva colección ( List<>
) con la llamada .ToList()
. Así que esa es una asignación (extra) redundante de una colección completa para mantener los valores.
Manera mucho más fácil:
Enum.GetValues(typeof(SomeEnum))
.Cast<SomeEnum>()
.Select(v => v.ToString())
.ToList();
Podrías usar el siguiente método genérico:
public static List<T> GetItemsList<T>(this int enums) where T : struct, IConvertible
{
if (!typeof (T).IsEnum)
{
throw new Exception("Type given must be an Enum");
}
return (from int item in Enum.GetValues(typeof (T))
where (enums & item) == item
select (T) Enum.Parse(typeof (T), item.ToString(new CultureInfo("en")))).ToList();
}
Si desea Enum int como clave y nombre como valor, está bien si almacena el número en la base de datos y ¡es de Enum!
void Main()
{
ICollection<EnumValueDto> list = EnumValueDto.ConvertEnumToList<SearchDataType>();
foreach (var element in list)
{
Console.WriteLine(string.Format("Key: {0}; Value: {1}", element.Key, element.Value));
}
/* OUTPUT:
Key: 1; Value: Boolean
Key: 2; Value: DateTime
Key: 3; Value: Numeric
*/
}
public class EnumValueDto
{
public int Key { get; set; }
public string Value { get; set; }
public static ICollection<EnumValueDto> ConvertEnumToList<T>() where T : struct, IConvertible
{
if (!typeof(T).IsEnum)
{
throw new Exception("Type given T must be an Enum");
}
var result = Enum.GetValues(typeof(T))
.Cast<T>()
.Select(x => new EnumValueDto { Key = Convert.ToInt32(x),
Value = x.ToString(new CultureInfo("en")) })
.ToList()
.AsReadOnly();
return result;
}
}
public enum SearchDataType
{
Boolean = 1,
DateTime,
Numeric
}
Siempre he usado para obtener una lista de valores de enum
como este:
Array list = Enum.GetValues(typeof (SomeEnum));
respuesta muy simple
Aquí hay una propiedad que uso en una de mis aplicaciones.
public List<string> OperationModes
{
get
{
return Enum.GetNames(typeof(SomeENUM)).ToList();
}
}
/// <summary>
/// Method return a read-only collection of the names of the constants in specified enum
/// </summary>
/// <returns></returns>
public static ReadOnlyCollection<string> GetNames()
{
return Enum.GetNames(typeof(T)).Cast<string>().ToList().AsReadOnly();
}
donde T es un tipo de enumeración; Agrega esto:
using System.Collections.ObjectModel;
Language[] result = (Language[])Enum.GetValues(typeof(Language))
List <SomeEnum> theList = Enum.GetValues(typeof(SomeEnum)).Cast<SomeEnum>().ToList();
private List<SimpleLogType> GetLogType()
{
List<SimpleLogType> logList = new List<SimpleLogType>();
SimpleLogType internalLogType;
foreach (var logtype in Enum.GetValues(typeof(Log)))
{
internalLogType = new SimpleLogType();
internalLogType.Id = (int) (Log) Enum.Parse(typeof (Log), logtype.ToString(), true);
internalLogType.Name = (Log)Enum.Parse(typeof(Log), logtype.ToString(), true);
logList.Add(internalLogType);
}
return logList;
}
en el código superior, el registro es un Enum y SimpleLogType es una estructura para los registros.
public enum Log
{
None = 0,
Info = 1,
Warning = 8,
Error = 3
}
public class NameValue
{
public string Name { get; set; }
public object Value { get; set; }
}
public class NameValue
{
public string Name { get; set; }
public object Value { get; set; }
}
public static List<NameValue> EnumToList<T>()
{
var array = (T[])(Enum.GetValues(typeof(T)).Cast<T>());
var array2 = Enum.GetNames(typeof(T)).ToArray<string>();
List<NameValue> lst = null;
for (int i = 0; i < array.Length; i++)
{
if (lst == null)
lst = new List<NameValue>();
string name = array2[i];
T value = array[i];
lst.Add(new NameValue { Name = name, Value = value });
}
return lst;
}
Convertir Enum a una lista más información disponible here .