¿Cuál es el valor predeterminado para la variable de enumeración?

Resuelto user496949 asked hace 13 años • 3 respuestas

Una variable de enumeración, ¿alguien sabe si siempre utiliza de forma predeterminada el primer elemento?

user496949 avatar Feb 11 '11 16:02 user496949
Aceptado

Es cualquier miembro de la enumeración que represente el valor 0. Específicamente, de la documentación :

El valor predeterminado de an enum Ees el valor producido por la expresión (E)0.

Como ejemplo, tome la siguiente enumeración:

enum E
{
    Foo, Bar, Baz, Quux
}

Sin anular los valores predeterminados, la impresión default(E)regresa Fooya que es el primer elemento que aparece.

Sin embargo, no siempre se da el caso de que 0una enumeración esté representada por el primer miembro. Por ejemplo, si haces esto:

enum F
{
    // Give each element a custom value
    Foo = 1, Bar = 2, Baz = 3, Quux = 0
}

La impresión default(F)te dará Quux, no Foo.

Si ninguno de los elementos de una enumeración Gcorresponde a 0:

enum G
{
    Foo = 1, Bar = 2, Baz = 3, Quux = 4
}

default(G)devuelve literalmente 0, aunque su tipo permanece como G(como se cita en los documentos anteriores, una conversión al tipo de enumeración dado).

BoltClock avatar Feb 11 '2011 09:02 BoltClock

Creo que es bastante peligroso confiar en el orden de los valores en una enumeración y asumir que el primero es siempre el predeterminado. Esta sería una buena práctica si le preocupa proteger el valor predeterminado.

enum E
{
    Foo = 0, Bar, Baz, Quux
}

De lo contrario, todo lo que se necesita es una refactorización descuidada del pedido y obtendrá un valor predeterminado completamente diferente.

user3154431 avatar Sep 13 '2016 11:09 user3154431

Puedes usar este fragmento :-D

using System;
using System.Reflection;

public static class EnumUtils
{
    public static T GetDefaultValue<T>()
        where T : struct, Enum
    {
        return (T)GetDefaultValue(typeof(T));
    }

    public static object GetDefaultValue(Type enumType)
    {
        var attribute = enumType.GetCustomAttribute<DefaultValueAttribute>(inherit: false);
        if (attribute != null)
            return attribute.Value;

        var innerType = enumType.GetEnumUnderlyingType();
        var zero = Activator.CreateInstance(innerType);
        if (enumType.IsEnumDefined(zero))
            return zero;

        var values = enumType.GetEnumValues();
        return values.GetValue(0);
    }
}

Ejemplo:

using System;

public enum Enum1
{
    Foo,
    Bar,
    Baz,
    Quux
}
public enum Enum2
{
    Foo  = 1,
    Bar  = 2,
    Baz  = 3,
    Quux = 0
}
public enum Enum3
{
    Foo  = 1,
    Bar  = 2,
    Baz  = 3,
    Quux = 4
}
[DefaultValue(Enum4.Bar)]
public enum Enum4
{
    Foo  = 1,
    Bar  = 2,
    Baz  = 3,
    Quux = 4
}

public static class Program 
{
    public static void Main() 
    {
        var defaultValue1 = EnumUtils.GetDefaultValue<Enum1>();
        Console.WriteLine(defaultValue1); // Foo

        var defaultValue2 = EnumUtils.GetDefaultValue<Enum2>();
        Console.WriteLine(defaultValue2); // Quux

        var defaultValue3 = EnumUtils.GetDefaultValue<Enum3>();
        Console.WriteLine(defaultValue3); // Foo

        var defaultValue4 = EnumUtils.GetDefaultValue<Enum4>();
        Console.WriteLine(defaultValue4); // Bar
    }
}
Piero Álvarez avatar Oct 09 '2020 13:10 Piero Álvarez