Cast problem in a generic method that receives an enum's array (enum [])

5

I want to make a generic method that gets a enum[] and returns a string representing the comma-separated array items.

public static string ToSeparatedCommaString<T>(T[] enums)
    where T : struct, IComparable, IFormattable, IConvertible//Não garante que seja enum mas sempre limita alguma coisa
{
    var commaString = string.Empty;
    foreach (var item in enums)
    {
        commaString += ((Enum)item).GetStringValue() + ",";
    }
    return commaString.TrimEnd(',');
}

The problem arises when I want to access the Extension Method GetStringValue() . Trying to cast cast , as you would expect, is not allowed.

Is there a way to achieve this?

GetStringValue() is a method that returns a string whose value is indicated in the attribute associated with the element of enum     

asked by anonymous 07.04.2015 / 18:27

2 answers

6

An easy way to solve the problem is to make the box of item into a object and then give another cast to the final type Enum .

Here are some suggestions:

  • Test the type of T to ensure that this is an enum type, and throw a descriptive exception to the problem that occurred if it is not

  • Using LINQ makes the code easier (I think, it's just a suggestion)

    return string.Join(",", enums.OfType<Enum>().Select(item => item.GetStringValue()));
    

    As I said GetStringValue is an extension method, you can do it as well:

    return string.Join(",", enums.OfType<Enum>().Select(NomeDaClasse.GetStringValue));
    

Final code ... without using LINQ because this is a matter of style and is personal:

public static string ToSeparatedCommaString<T>(T[] enums)
    where T : struct, IComparable, IFormattable, IConvertible
{
    if (!typeof(T).IsEnum)
        throw new Exception("O método de extensão 'ToSeparatedCommaString' suporta apenas Enums no parâmetro genérico 'T'.");

    var commaString = string.Empty;
    foreach (var item in enums)
    {
        commaString += ((Enum)(object)item).GetStringValue() + ",";
    }
    return commaString.TrimEnd(',');
}
    
07.04.2015 / 18:49
3

You know that without giving the guarantee, you can not have a reliable code, so you'll have to solve it at runtime if you can do the operation or not. There are some possible ways, some better than others, some will give you more power to manipulate the error if it occurs. You can do this:

public static string ToSeparatedCommaString<T>(T[] enums)
    where T : struct, IComparable, IFormattable, IConvertible {
    var commaString = string.Empty;
    if (!typeof(T).IsEnum) {
        throw new ArgumentException("Tipo de enums é inválido");
    }
    foreach (var item in enums) {
        Enum enumerador = item as Enum;
        commaString += enumerador.GetStringValue() + ",";
    }
    return commaString.TrimEnd(',');
}

See working on dotNetFiddle .

I did a performance comparison of the approach I proposed with that of Miguel's answer that resolves well as well. The result of this was better. This was discussed in the comments below.

    
07.04.2015 / 19:03