문제

I try to display enum values using the enums ToString method. The enum has the Flags attribute.

There are values that don't match any combination of the enum values.
In this case, ToString returns the number as decimal, but I want to display it as a hex string.

Using ToString("X8") will always return the hex value.

I tried Enum.IsDefined, but it returns only true on non-combined values.

Example:

0x00000201 -> "XXt, TSW_AUTO_DETECT"   (known values)
0x00010108 -> "00010108"               (unknown value)

Q: How to "ToString" unknown enum values as hex value?

도움이 되었습니까?

해결책

You could check if the value has any other bits set than the total bit mask of the flags enumeration. If so, return the number, otherwise the normal tostring:

public static string GetDescription(EnumName value)
{
    var enumtotal = Enum.GetValues(typeof(EnumName)).Cast<int>().Aggregate((i1, i2) => i1 | i2); //this could be buffered for performance
    if ((enumtotal | (int)value) == enumtotal)
        return value.ToString();
    return ((int)value).ToString("X8");
}

다른 팁

You need to write your own string convertion routine, you can't override ToString() for enums. In order to format [Flags] look at System.Enum.InternalFlagsFormat:

private static String InternalFlagsFormat(RuntimeType eT, Object value)
    {
        Contract.Requires(eT != null);
        Contract.Requires(value != null); 
        ulong result = ToUInt64(value);
        HashEntry hashEntry = GetHashEntry(eT); 
        // These values are sorted by value. Don't change this 
        String[] names = hashEntry.names;
        ulong[] values = hashEntry.values; 
        Contract.Assert(names.Length == values.Length);

        int index = values.Length - 1;
        StringBuilder retval = new StringBuilder(); 
        bool firstTime = true;
        ulong saveResult = result; 

        // We will not optimize this code further to keep it maintainable. There are some boundary checks that can be applied
        // to minimize the comparsions required. This code works the same for the best/worst case. In general the number of 
        // items in an enum are sufficiently small and not worth the optimization.
        while (index >= 0)
        {
            if ((index == 0) && (values[index] == 0)) 
                break;

            if ((result & values[index]) == values[index]) 
            {
                result -= values[index]; 
                if (!firstTime)
                    retval.Insert(0, enumSeperator);

                retval.Insert(0, names[index]); 
                firstTime = false;
            } 

            index--;
        } 

        // We were unable to represent this number as a bitwise or of valid flags
        if (result != 0)
            return value.ToString(); 

        // For the case when we have zero 
        if (saveResult==0) 
        {
            if (values.Length > 0 && values[0] == 0) 
                return names[0]; // Zero was one of the enum values.
            else
                return "0";
        } 
        else
        return retval.ToString(); // Return the string representation 
    } 
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top