C#的DataBinder.Eval是否有快速版本?

myt*_*thz 3 c# expression eval compilation

我想看一下ASP.NET的System.Web.UI.DataBinder.Eval()的快速版本是否存在?理想情况下编译为Func的东西我可以缓存并稍后调用,例如:

Func<object,string> expr = CompileDataBinder(typeof(Model), "model.PocoProperty.Name");
string propertyName = expr(model);
Run Code Online (Sandbox Code Playgroud)

有谁知道这样的野兽是否存在?

PS我没有使用ASP.NET,并希望它能在普通的C#中工作

Mar*_*ell 6

我看的越多,我就越想说:

Func<Model,string> expr = model => model.PocoProperty.Name;
Run Code Online (Sandbox Code Playgroud)

如果您需要基于字符串,ExpressionAPI在那里非常公平.

class Program
{
    static void Main(string[] args)
    {
        Func<object, string> expr = CompileDataBinder(typeof(Model), "PocoProperty.Name");

        var model = new Model { PocoProperty = new ModelPoco { Name = "Foo" } };

        string propertyName = expr(model);
    }
    static Func<object, string> CompileDataBinder(Type type, string expr)
    {
        var param = Expression.Parameter(typeof(object));
        Expression body = Expression.Convert(param, type);
        var members = expr.Split('.');
        for (int i = 0; i < members.Length;i++ )
        {
            body = Expression.PropertyOrField(body, members[i]);
        }
        var method = typeof(Convert).GetMethod("ToString", BindingFlags.Static | BindingFlags.Public,
            null, new Type[] { body.Type }, null);
        if (method == null)
        {
            method = typeof(Convert).GetMethod("ToString", BindingFlags.Static | BindingFlags.Public,
                null, new Type[] { typeof(object)}, null);
            body = Expression.Call(method, Expression.Convert(body, typeof(object)));
        }
        else
        {
            body = Expression.Call(method, body);
        }

        return Expression.Lambda<Func<object, string>>(body, param).Compile();
    }
}

class Model
{
    public ModelPoco PocoProperty { get; set; }
}
class ModelPoco
{
    public string Name { get; set; }
}
Run Code Online (Sandbox Code Playgroud)