Comment puis-je obtenir la valeur max int à partir d'une énumération en utilisant des génériques?
J'ai essayé ce qui suit mais cela affiche l'erreur de compilation suivante:
Impossible de convertir implicitement T en int
int maxValue = GetMaxValue<SomeEnum>(typeof(SomeEnum)); //expecting 2 private static int GetMaxValue<T>(Type enumType) { return Enum.GetValues(enumType).Cast<T>().Max(); } public enum SomeEnum { ValueOne = 1, Value = 2 }
3 Réponses :
Vous devez diffuser en int
, pas en T
. Et vous n'avez pas réellement besoin du paramètre Type
(sauf si vous ne connaissez pas le type au moment de la compilation), car vous pouvez simplement faire typeof (T)
:
private static U GetMaxValue<T, U>() where U : struct { return Enum.GetValues(typeof(T)).Cast<U>().Max(); } // usage: GetMaxValue<SomeLongEnum, long>()
Si vos énumérations ont long
ou un autre type comme type sous-jacent, vous pouvez spécifier un autre paramètre de type pour les convertir:
private static int GetMaxValue<T>() { return Enum.GetValues(typeof(T)).Cast<int>().Max(); } // usage: GetMaxValue<SomeEnum>() // 2
Cela ne fonctionnera pas si votre énumération est définie comme long
(ou byte
ou short
). Mieux vaut utiliser Convert.ToInt32
pour couvrir ces cas (bien que cela ne couvre évidemment pas le cas de débordement avec long
, mais il n'y a aucun moyen de le couvrir avec cette signature)
Je pense que vous pouvez avoir une énumération longue
simplement en la castant ( int
est la valeur par défaut), donc lorsque vous renvoyez à int
cela ne devrait pas créer des problèmes, non?
@ALFA Ce sera le cas si la valeur est supérieure à int.MaxValue
@KevinGosse Je pense que vous ne pouvez pas avoir une valeur plus grande que int.MaxValue
si pour avoir une énumération longue
vous devez d'abord lancer un int < / code> au type
long
.
Une énumération est un ensemble de constantes nommées dont le type sous-jacent est n'importe quel type intégral , Enum Class .
@ALFA Je ne sais pas pourquoi vous supposez que vous devez effectuer un cast de int à long. public enum SomeEnum: long {ValueOne = 30000000000}
est valide
@KevinGosse vous avez raison, j'étais sûr que la seule façon d'avoir une longue énumération était de la lancer à partir d'une énumération int. Je l'ai maintenant merci :)
Dans le cas de C # 7.3 ou version ultérieure, vous pouvez implémenter l'idée de Sweeper d'une manière un peu différente (avec l'aide de Veuillez noter que le résultat est où T: Enum code> contrainte):
public static T GetMaxValue<T>() where T : Enum {
return Enum.GetValues(typeof(T)).Cast<T>().Max();
}
...
SomeEnum max = GetMaxValue<SomeEnum>();
enum
lui-même et c'est pourquoi nous n'avons aucun problème avec le type sous-jacent enum ( octet
, court
int
, long
)
Utilisez Convert.ToInt32
public enum SomeEnum { ValueOne = 1, Value = 2, END } return (int)(SomeEnum.END - 1);
Mais en général, je fais cela, plus rapidement que d'appeler GetValues
return Convert.ToInt32(Enum.GetValues(enumType).Cast<T>().Max());
Enum ne peut être défini que comme int, pourquoi devriez-vous utiliser des génériques et essayer de les convertir?
@ALFA En fait, une énumération peut également être définie comme octet, court ou long