enum
C #에서 어떻게 열거 할 수 있습니까?
예를 들어 다음 코드는 컴파일되지 않습니다.
public enum Suit
{
Spades,
Hearts,
Clubs,
Diamonds
}
public void EnumerateAllSuitsDemoMethod()
{
foreach (Suit suit in Suit)
{
DoSomething(suit);
}
}
그리고 다음과 같은 컴파일 타임 오류가 발생합니다.
‘정장’은 ‘유형’이지만 ‘변수’처럼 사용됩니다.
Suit
두 번째 키워드 인 키워드에서는 실패합니다 .
답변
foreach (Suit suit in (Suit[]) Enum.GetValues(typeof(Suit)))
{
}
참고 : 캐스트 (Suit[])
는 반드시 필요한 것은 아니지만 코드를 0.5ns 더 빠르게 만듭니다.
답변
값이 아닌 각 열거 형의 이름을 실제로 인쇄하려는 것처럼 보입니다. 어떤 경우 Enum.GetNames()
에는 올바른 접근법 인 것 같습니다.
public enum Suits
{
Spades,
Hearts,
Clubs,
Diamonds,
NumSuits
}
public void PrintAllSuits()
{
foreach (string name in Enum.GetNames(typeof(Suits)))
{
System.Console.WriteLine(name);
}
}
그건 그렇고, 값을 증가시키는 것은 열거 형의 값을 열거하는 좋은 방법이 아닙니다. 대신이 작업을 수행해야합니다.
Enum.GetValues(typeof(Suit))
대신에 사용하겠습니다 .
public enum Suits
{
Spades,
Hearts,
Clubs,
Diamonds,
NumSuits
}
public void PrintAllSuits()
{
foreach (var suit in Enum.GetValues(typeof(Suits)))
{
System.Console.WriteLine(suit.ToString());
}
}
답변
쉬운 열거 형 사용을 위해 몇 가지 확장을 만들었습니다. 누군가가 그것을 사용할 수 있습니다 …
public static class EnumExtensions
{
/// <summary>
/// Gets all items for an enum value.
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="value">The value.</param>
/// <returns></returns>
public static IEnumerable<T> GetAllItems<T>(this Enum value)
{
foreach (object item in Enum.GetValues(typeof(T)))
{
yield return (T)item;
}
}
/// <summary>
/// Gets all items for an enum type.
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="value">The value.</param>
/// <returns></returns>
public static IEnumerable<T> GetAllItems<T>() where T : struct
{
foreach (object item in Enum.GetValues(typeof(T)))
{
yield return (T)item;
}
}
/// <summary>
/// Gets all combined items from an enum value.
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="value">The value.</param>
/// <returns></returns>
/// <example>
/// Displays ValueA and ValueB.
/// <code>
/// EnumExample dummy = EnumExample.Combi;
/// foreach (var item in dummy.GetAllSelectedItems<EnumExample>())
/// {
/// Console.WriteLine(item);
/// }
/// </code>
/// </example>
public static IEnumerable<T> GetAllSelectedItems<T>(this Enum value)
{
int valueAsInt = Convert.ToInt32(value, CultureInfo.InvariantCulture);
foreach (object item in Enum.GetValues(typeof(T)))
{
int itemAsInt = Convert.ToInt32(item, CultureInfo.InvariantCulture);
if (itemAsInt == (valueAsInt & itemAsInt))
{
yield return (T)item;
}
}
}
/// <summary>
/// Determines whether the enum value contains a specific value.
/// </summary>
/// <param name="value">The value.</param>
/// <param name="request">The request.</param>
/// <returns>
/// <c>true</c> if value contains the specified value; otherwise, <c>false</c>.
/// </returns>
/// <example>
/// <code>
/// EnumExample dummy = EnumExample.Combi;
/// if (dummy.Contains<EnumExample>(EnumExample.ValueA))
/// {
/// Console.WriteLine("dummy contains EnumExample.ValueA");
/// }
/// </code>
/// </example>
public static bool Contains<T>(this Enum value, T request)
{
int valueAsInt = Convert.ToInt32(value, CultureInfo.InvariantCulture);
int requestAsInt = Convert.ToInt32(request, CultureInfo.InvariantCulture);
if (requestAsInt == (valueAsInt & requestAsInt))
{
return true;
}
return false;
}
}
열거 형 자체는 FlagsAttribute 로 장식되어야합니다 .
[Flags]
public enum EnumExample
{
ValueA = 1,
ValueB = 2,
ValueC = 4,
ValueD = 8,
Combi = ValueA | ValueB
}
답변
.NET 프레임 워크의 일부 버전은 지원하지 않습니다 Enum.GetValues
. 다음은 Ideas 2.0 의 좋은 해결 방법 입니다. Compact Framework의 Enum.GetValues :
public Enum[] GetValues(Enum enumeration)
{
FieldInfo[] fields = enumeration.GetType().GetFields(BindingFlags.Static | BindingFlags.Public);
Enum[] enumerations = new Enum[fields.Length];
for (var i = 0; i < fields.Length; i++)
enumerations[i] = (Enum) fields[i].GetValue(enumeration);
return enumerations;
}
리플렉션 과 관련된 코드와 마찬가지로 코드가 한 번만 실행되고 결과가 캐시되도록 조치를 취해야합니다.
답변
사용 Cast<T>
:
var suits = Enum.GetValues(typeof(Suit)).Cast<Suit>();
당신은 간다 IEnumerable<Suit>
.
답변
GetValues()
루프가있을 때마다 호출되지 않기 때문에 이것이 다른 제안보다 효율적이라고 생각합니다 . 더 간결합니다. 그리고 Suit
가 아닌 경우 런타임 예외 가 아닌 컴파일 타임 오류가 발생 합니다 enum
.
EnumLoop<Suit>.ForEach((suit) => {
DoSomethingWith(suit);
});
EnumLoop
이 완전히 일반적인 정의가 있습니다.
class EnumLoop<Key> where Key : struct, IConvertible {
static readonly Key[] arr = (Key[])Enum.GetValues(typeof(Key));
static internal void ForEach(Action<Key> act) {
for (int i = 0; i < arr.Length; i++) {
act(arr[i]);
}
}
}
답변
당신은받지 않습니다 Enum.GetValues()
에 실버 .
Einar Ingebrigtsen의 원본 블로그 게시물 :
public class EnumHelper
{
public static T[] GetValues<T>()
{
Type enumType = typeof(T);
if (!enumType.IsEnum)
{
throw new ArgumentException("Type '" + enumType.Name + "' is not an enum");
}
List<T> values = new List<T>();
var fields = from field in enumType.GetFields()
where field.IsLiteral
select field;
foreach (FieldInfo field in fields)
{
object value = field.GetValue(enumType);
values.Add((T)value);
}
return values.ToArray();
}
public static object[] GetValues(Type enumType)
{
if (!enumType.IsEnum)
{
throw new ArgumentException("Type '" + enumType.Name + "' is not an enum");
}
List<object> values = new List<object>();
var fields = from field in enumType.GetFields()
where field.IsLiteral
select field;
foreach (FieldInfo field in fields)
{
object value = field.GetValue(enumType);
values.Add(value);
}
return values.ToArray();
}
}