为什么会出现没有在C#`fieldof`或`methodof`操作? [关闭](Why is t

2019-06-17 21:46发布

他们可以使用如下:

FieldInfo field = fieldof(string.Empty);
MethodInfo method1 = methodof(int.ToString);
MethodInfo method2 = methodof(int.ToString(IFormatProvider));

fieldof可以被编译为IL为:

ldtoken <field>
call FieldInfo.GetFieldFromHandle

methodof可以被编译成IL为:

ldtoken <method>
call MethodBase.GetMethodFromHandle

每当typeof使用运营商,你会得到完美的查找所有引用的结果。 不幸的是,只要你去的字段或方法,你结束了讨厌的黑客。 我认为你可以做到以下几点...或者你可以回去通过名字得到一个领域。

public static FieldInfo fieldof<T>(Expression<Func<T>> expression)
{
    MemberExpression body = (MemberExpression)expression.Body;
    return (FieldInfo)body.Member;
}

public static MethodInfo methodof<T>(Expression<Func<T>> expression)
{
    MethodCallExpression body = (MethodCallExpression)expression.Body;
    return body.Method;
}

public static MethodInfo methodof(Expression<Action> expression)
{
    MethodCallExpression body = (MethodCallExpression)expression.Body;
    return body.Method;
}

public static void Test()
{
    FieldInfo field = fieldof(() => string.Empty);
    MethodInfo method1 = methodof(() => default(string).ToString());
    MethodInfo method2 = methodof(() => default(string).ToString(default(IFormatProvider)));
    MethodInfo method3 = methodof(() => default(List<int>).Add(default(int)));
}

Answer 1:

埃里克利珀(在C#设计团队)对这个话题很好的概括/讨论在这里 。 报价:

这是一个真棒功能,几乎每个人都参与到设计过程中希望我们可以做,但也有我们为什么不选择好实际的原因。 如果没有设计它,实现它是我们可以用我们的预算有限的最好方式,当一天到来时,我们会做到这一点。 在此之前,使用反射。



Answer 2:

实际上,你可以尽量避免使用反射和lambda表达式(.NET Framework 2.0中)。 考虑下面的类:

public class methodof<T>
{
    private MethodInfo method;

    public methodof(T func)
    {
        Delegate del = (Delegate)(object)func;
        this.method = del.Method;
    }

    public static implicit operator methodof<T>(T methodof)
    {
        return new methodof<T>(methodof);
    }

    public static implicit operator MethodInfo(methodof<T> methodof)
    {
        return methodof.method;
    }
}

和它的用法:

MethodInfo writeln = (methodof<Action>)Console.WriteLine;
MethodInfo parse = (methodof<Func<string, int>>)int.Parse;


Answer 3:

@ 280Z28 - 我们只是坐下来弄清楚如何做到这一点的时候,我发现你的问题和代码。 我们需要一个性能中的方法,所以我加入吧。 这是以防别人需要它。 THX的大问题。

     public static PropertyInfo PropertyOf<T>(Expression<Func<T>> expression)
    {
        MemberExpression body = (MemberExpression)expression.Body;
        PropertyInfo pi = body.Member as PropertyInfo;
        if (pi != null)
        {
            return pi;
        }
        else throw new ArgumentException("Lambda must be a Property.");
    } 

      [TestMethod()]
    public void MethodofPropertyOfTest<T>()
    {

        string foo = "Jamming";
        MethodInfo method1 = ReflectionHelper.Methodof(() => default(string).ToString());
        PropertyInfo prop = ReflectionHelper.PropertyOf(() => default(string).Length);
        Assert.AreEqual(method1.Invoke(foo, null), "Jamming");
        Assert.AreEqual(prop.GetGetMethod().Invoke(foo, null), foo.Length);
    }


Answer 4:

这是一个通用型的版本,可以用F2重命名,而不是需要的例子修改存在的代​​码,方法名是GetPKValue

var typFactory = typeof(FormFieldFactory<>).MakeGenericType(entity.GetType());
var methodName = new Func<object, object>(FormFieldFactory<object>.GetPKValue).Method.Name;

var theMethod =
    (Func<object, object>)Delegate.CreateDelegate(
        typeof(Func<object, object>)
        , typFactory.GetMethod(methodName)
    );


Answer 5:

我后悔的一天,当反射变得如此简单。 如果你认为动态SQL是坏的,这将导致一些十几次差。

试想一下,更改属性名称,不必担心运行时错误。 /不寒而栗



文章来源: Why is there not a `fieldof` or `methodof` operator in C#? [closed]
标签: c# reflection