using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading.Tasks;
namespace Yi.Framework.Infrastructure.Helper
{
public static class ExpressionHelper
{
///
/// Expression表达式树lambda参数拼接组合
///
///
///
///
///
///
public static Expression Compose(this Expression first, Expression second, Func merge)
{
var parameterMap = first.Parameters.Select((f, i) => new { f, s = second.Parameters[i] }).ToDictionary(p => p.s, p => p.f);
var secondBody = LambdaParameteRebinder.ReplaceParameter(parameterMap, second.Body);
return Expression.Lambda(merge(first.Body, secondBody), first.Parameters);
}
///
/// Expression表达式树lambda参数拼接--false
///
///
///
public static Expression> False() => f => false;
///
/// Expression表达式树lambda参数拼接-true
///
///
///
public static Expression> True() => f => true;
///
/// Expression表达式树lambda参数拼接--and
///
///
///
///
///
public static Expression> And(this Expression> first, Expression> second) => first.Compose(second, Expression.And);
///
/// Expression表达式树lambda参数拼接--or
///
///
///
///
///
public static Expression> Or(this Expression> first, Expression> second) => first.Compose(second, Expression.Or);
}
public class LambdaParameteRebinder : ExpressionVisitor
{
///
/// 存放表达式树的参数的字典
///
private readonly Dictionary map;
///
/// 构造函数
///
///
public LambdaParameteRebinder(Dictionary map)
{
this.map = map ?? new Dictionary();
}
///
/// 重载参数访问的方法,访问表达式树参数,如果字典中包含,则取出
///
/// 表达式树参数
///
protected override Expression VisitParameter(ParameterExpression node)
{
if (map.TryGetValue(node, out ParameterExpression expression))
{
node = expression;
}
return base.VisitParameter(node);
}
public static Expression ReplaceParameter(Dictionary map, Expression exp)
{
return new LambdaParameteRebinder(map).Visit(exp);
}
}
}