正在使用类型变量转换为枚举



我的部分软件使用反射。我遇到的问题是,虽然我可以获取属性的类型,但无法使用PropertyInfo中的Type转换字符串值。这就是我在示例代码中使用t的原因。

下面的代码以代码注释的形式演示了错误消息的问题。语法错误出现在t上。我该如何解决这个问题?感谢

class Program
{
    static void Main(string[] args)
    {
        Type t = typeof(Letters);
        Letters letter = "A".ToEnum<t>(); //-- Type or namespace expected.
    }
}
public enum Letters { A, B, C }
//-- This is a copy of the EmunHelper functions from our tools library.
public static class EnumExt
{
    public static T ToEnum<T>(this string @string)
    {
        int tryInt;
        if (Int32.TryParse(@string, out tryInt)) return tryInt.ToEnum<T>();
        return (T)Enum.Parse(typeof(T), @string);
    }
    public static T ToEnum<T>(this int @int)
    {
        return (T)Enum.ToObject(typeof(T), @int);
    }
}

解决方案:

以下操作之所以有效,是因为当使用反射设置值时,会接受Enum的实际类型。其中myObject.Letter = result不是。

Type t = currentProperty.PropertyType;
Enum result = Enum.Parse(t, @string) as Enum;
ReflectionHelper.SetProperty(entity, "LetterPropertyName", result);

谢谢大家的帮助。

Enum.Parse(t, @string) as Enum;

这实现了与您发布的解决方案相同的功能。

要能够调用泛型方法,必须在编译时知道类型。您使用的语法无效。

为了能够调用你的方法,你必须使用反射来获得对正确通用函数的引用,这样你才能调用它

public static object ToEnum(this string s, Type type)
{
    var eeType = typeof(EnumExt);
    var method = eeType.GetMethod("ToEnum", new[] { typeof(string) })
                       .MakeGenericMethod(type);
    return method.Invoke(null, new[] { s });
}

然后你可以称之为:

Letters letter = (Letters)"A".ToEnum(t);

p.s.,我强烈建议您将变量名称更改为其他名称。仅仅因为你可以将变量命名为关键字,并不意味着你应该这样做。

我不是反射方面的专家,但这很有效:

static void Main(string[] args)
{
    Type t = typeof(Letters);
    MethodInfo info = typeof(EnumExt).GetMethod("ToEnum", new Type[] { typeof(string) });
    var method = info.MakeGenericMethod(new Type[] { t });
    var result = (Letters)method.Invoke(null, new [] { "A" });            
    Console.ReadLine();
}

我认为你的问题可以通过两种方式理解:i( 您想修复语法错误ii(您需要为您提供的功能提供一个有效的实现

对于i(,我建议您更改:

Letters letter = "A".ToEnum<t>()

进入

Letters letter = "A".ToEnum<Letters>()

因为泛型是在编译时求解的,所以不能将变量用作参数。

对于ii(,您可以更改提供类型参数的方式,从"泛型"参数更改为"普通"参数(如Jeff Mercado所建议的(。通过这样做,您的功能原型变成:

public static T ToEnum(this string @string, Type t)

最后,我要谈两点:

  • 根据我的经验,反思是非常缓慢的。我曾经写过一个汇编解析器,它大量使用枚举上的反射来获取寄存器名。当一个没有任何反射的等效版本在不到10秒内执行时,它通常会运行几分钟(这让VS调试器抱怨没有响应能力(。

  • 正如Jeff Mercado所指出的,我看不出有什么好的理由让你对类型名和变量名使用相同的vocal

相关内容

  • 没有找到相关文章