使用:
var pepole = new Pepole
{
age = 32,
Id = 199,
Name = "中国"
};
Expression<Func<Pepole, bool>> exception = p => p.Id == pepole.Id && (p.Name == pepole.Name || p.age > pepole.age);
ExpressionVisitorToSQL expressionVisitorToSQL = new ExpressionVisitorToSQL();
expressionVisitorToSQL.Visit(exception);
string sqlCondition = expressionVisitorToSQL.GetSqlCondtion();
SQL条件拼接类
public class ExpressionVisitorToSQL : ExpressionVisitor
{
private Stack<string> _sqlCondition = new Stack<string>();
/// <summary>
/// 符号转投
/// </summary>
/// <param name="expressionType"></param>
/// <returns></returns>
private string GetSqlOpereatorByNodeType(ExpressionType expressionType)
{
switch (expressionType)
{
case ExpressionType.AndAlso:
return "and";
case ExpressionType.OrElse:
return "or";
case ExpressionType.GreaterThan:
return ">";
case ExpressionType.Equal:
return "=";
default:
return "**";
}
}
/// <summary>
/// 二元遍历
/// </summary>
/// <param name="node"></param>
/// <returns></returns>
protected override Expression VisitBinary(BinaryExpression node)
{
_sqlCondition.Push(")");
base.Visit(node.Right);
_sqlCondition.Push(GetSqlOpereatorByNodeType(node.NodeType));
base.Visit(node.Left);
_sqlCondition.Push("(");
return node;
}
/// <summary>
/// 成员遍历
/// </summary>
/// <param name="node"></param>
/// <returns></returns>
protected override Expression VisitMember(MemberExpression node)
{
if (node.Expression.NodeType == ExpressionType.Parameter)
{
_sqlCondition.Push($"`{node.Member.Name}`");
return node;
}
else if (node.Expression.NodeType == ExpressionType.MemberAccess)
{
var objectMember = Expression.Convert(node, typeof(object));
var getterLambda = Expression.Lambda<Func<object>>(objectMember);
var getterValue = getterLambda.Compile()();
_sqlCondition.Push($"`{getterValue}`");
return node;
}
return base.VisitMember(node);
}
/// <summary>
/// 常量
/// </summary>
/// <param name="node"></param>
/// <returns></returns>
protected override Expression VisitConstant(ConstantExpression node)
{
if (node.Value.GetType().IsValueType || node.Value.GetType().Name == "String")
{
_sqlCondition.Push(node.Value.ToString());
return node;
}
else
{
return base.VisitConstant(node);
}
}
/// <summary>
/// 条件拼接
/// </summary>
/// <returns></returns>
public string GetSqlCondtion()
{
return string.Join(" ", _sqlCondition.ToArray());
}
}