Невозможно преобразовать тип 'System.Enum' в int
(Хорошо, я расскажу о глубинах моего невежества здесь, пожалуйста, будьте осторожны)
Фон
У меня есть метод, который выглядит (немного) следующим образом:
public void AddLink(Enum enumVal)
{
string identifier = m_EnumInterpreter(enumVal);
AddLink(identifier);
}
EnumInterpreter - это строка Func < Enum, которая передается при создании родительского класса.
Я использую Enum, потому что на этом уровне это "ничто из моего бизнеса" - мне все равно, какой конкретный enum он есть. Вызывающий код просто использует (сгенерированное) перечисление, чтобы избежать магических строк.
Вопрос
Если EnumInterpreter отправляет обратно пустую строку, я хотел бы сделать исключение с фактическим значением enumVal. Я думал, что просто смогу использовать int, но у компилятора его не будет. Что я делаю не так? (Пожалуйста, не говорите "все" ).
Ответы
Ответ 1
System.Enum не может быть напрямую передан Integer, но он явно реализует IConvertible, то есть вы можете использовать следующее:
public void AddLink(Enum enumVal)
{
string identifier = m_EnumInterpreter(Convert.ToInt32(enumVal));
AddLink(identifier);
}
Имейте в виду, что если ваш Enum фактически использует что-то другое, кроме Integer (например, float), вы потеряете нецелые данные при преобразовании. Или, очевидно, замените вызов Convert тем, с чего вы конвертируете (если он известен)
Ответ 2
Нет, вы не можете передать его в int, потому что System.Enum не является перечислением, это просто базовый класс для перечислений.
EDIT:
Вы можете получить значение следующим образом, но оно уродливо:
int intVar = (int)enuYourEnum.GetType().GetField("value__").GetValue(objYourEnum);
Ответ 3
попробуйте это.
m_EnumInterpreter ((int) (объект) enumVal);
Ответ 4
Различные вещи здесь:
1) ответ Райана выглядит нормально, но... Я предпочел бы передать Enum до интерпретатора перечисления, чтобы вы могли сделать весь Convert.To... там. Если вы знаете, что используете ТОЛЬКО целочисленные перечисления, Convert.ToInt32() просто отлично. В противном случае вы можете добавить, используя либо отражение, либо try/catch других преобразований.
2) Вы также можете рассмотреть возможность использования членов класса Enum, таких как .GetName(),.GetValue() и т.д., поскольку они напрямую связаны с определенными именами и значениями, не зависящими от типа перечисления.
3) технически я бы не выбрал исключение вне интерпретатора перечисления. Если это условие в целом истинно, выкиньте исключение из интерпретатора перечисления, так что все применения класса будут полезны для проверки. Или вы можете в конечном итоге дублировать код.
4) у вас, похоже, есть фон С++/MFC, судящий из вашего имени переменной. Вы можете захотеть войти в соглашения об именах в стиле С#, это облегчит вам жизнь при использовании/чтении кода и библиотек других людей. Ознакомьтесь с MS StyleCop для хорошего добавления, чтобы помочь с именованием.
Ответ 5
Я не знаю, включать ли это в мой вопрос или как ответ. Проблема в том, что это не ответ, но это ответ, который работает для меня.
То, что я случайно обнаружил при попытке чего-то другого, заключается в том, что если я просто ввожу его в конец строки, я получаю то, что хочу:
throw new Exception("EnumInterpreter returns empty string for enumVal=" + enumVal);
//EnumInterpreter returns empty string for enumVal=3720116125
Я фактически упростил int в моем вопросе, реальный тип данных - uint (в данном конкретном случае). К счастью, учитывая, что я только на самом деле хотел строку, мне не о чем беспокоиться.
Я не уверен, какой из трех других ответов "прав", поэтому проголосуйте...
Ответ 6
Я понимаю, что это, вероятно, не решение вашей конкретной проблемы, но я просто хочу опубликовать, как я решил это для конкретного API, который я использовал.
int result = (int) (ActualEnumType) MethodThatReturnsSystemEnumType( arg1, arg2 );
Надеюсь, это поможет кому-то. Double cast FTW.
Ответ 7
Почему бы не разобрать перечисление на строку и не вернуть фактическое значение перечисления?
public enum MyEnum { Flower = 1, Tree = 2, Animal = 3 };
string name = MyEnum.Flower.ToString(); // returns "Flower"
Я думаю, что .ToString()
устарел, и я не уверен в его новом способе. Я бы подумал, что фактическое представление перечисления было бы более полезным, чем int?