微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

Expression <Func <在T,bool >>或Expression <Func <TBase,bool >>到Expression <Func <T,bool >>转换器

如何解决Expression <Func <在T,bool >>或Expression <Func <TBase,bool >>到Expression <Func <T,bool >>转换器

|| 有没有简单的转换方法
Expression<Func<TBase,bool>> 
Expression<Func<T,bool>>
T是从TBase继承的?     

解决方法

        只要T从TBase派生,就可以使用原始表达式的主体和参数直接创建所需类型的表达式。
Expression<Func<object,bool>> x = o => o != null;
Expression<Func<string,bool>> y = Expression.Lambda<Func<string,bool>>(x.Body,x.Parameters);
    ,        您可能需要手动转换。原因是您正在有效地转换为可能的子集。所有
T
均为
TBase
,但并非所有
TBase
均为
T
。 好消息是,您可以使用Expression.Invoke进行此操作,然后将适当的强制转换/转换手动应用于
TBase
(当然会遇到任何类型安全问题)。 编辑:对于造成的误解,我深表歉意。我认为,简单地转换表达式仍然是您最好的选择。它使您能够根据需要处理转换。马克·格雷夫(Marc Gravell)的答案是我见过的最简洁明了的方法。     ,        为此,我用重载VisitLambda和VisitParameter编写了ExpressionVisitor 这里是:
public class ConverterExpressionVisitor<TDest> : ExpressionVisitor
{
    protected override Expression VisitLambda<T>(Expression<T> node)
    {
        var readOnlyCollection = node.Parameters.Select(a => Expression.Parameter(typeof(TDest),a.Name));
        return Expression.Lambda(node.Body,node.Name,readOnlyCollection);
    }

    protected override Expression VisitParameter(ParameterExpression node)
    {
        return Expression.Parameter(typeof(TDest),node.Name);
    }
}

public class A { public string S { get; set; } }
public class B : A { }

static void Main(string[] args)
{
    Expression<Func<A,bool>> ExpForA = a => a.S.StartsWith(\"Foo\");
    Console.WriteLine(ExpForA); // a => a.S.StartsWith(\"Foo\");

    var converter = new ConverterExpressionVisitor<B>();
    Expression<Func<B,bool>> ExpForB = (Expression<Func<B,bool>>)converter.Visit(ExpForA);
    Console.WriteLine(ExpForB); // a => a.S.StartsWith(\"Foo\"); - same as for A but for B
    Console.ReadLine();
}
    

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。