private HqlTreeNode TranslateInequalityComparison(BinaryExpression expression) { var lhs = VisitExpression(expression.Left).ToArithmeticExpression(); var rhs = VisitExpression(expression.Right).ToArithmeticExpression(); // Check for nulls on left or right. if (VisitorUtil.IsNullConstant(expression.Right)) { rhs = null; } if (VisitorUtil.IsNullConstant(expression.Left)) { lhs = null; } if (lhs == null && rhs == null) { return(_hqlTreeBuilder.False()); } if (lhs == null) { return(_hqlTreeBuilder.IsNotNull(rhs)); } if (rhs == null) { return(_hqlTreeBuilder.IsNotNull(lhs)); } var lhsNullable = _nullableExpressionDetector.IsNullable(expression.Left, expression); var rhsNullable = _nullableExpressionDetector.IsNullable(expression.Right, expression); var inequality = _hqlTreeBuilder.Inequality(lhs, rhs); if (!lhsNullable && !rhsNullable) { return(inequality); } var lhs2 = VisitExpression(expression.Left).ToArithmeticExpression(); var rhs2 = VisitExpression(expression.Right).ToArithmeticExpression(); HqlBooleanExpression booleanExpression; if (lhsNullable && rhsNullable) { booleanExpression = _hqlTreeBuilder.Inequality( _hqlTreeBuilder.IsNull(lhs2).ToArithmeticExpression(), _hqlTreeBuilder.IsNull(rhs2).ToArithmeticExpression()); } else if (lhsNullable) { booleanExpression = _hqlTreeBuilder.IsNull(lhs2); } else { booleanExpression = _hqlTreeBuilder.IsNull(rhs2); } return(_hqlTreeBuilder.BooleanOr(inequality, booleanExpression)); }
protected HqlTreeNode VisitBinaryExpression(BinaryExpression expression) { var lhs = VisitExpression(expression.Left).AsExpression(); var rhs = VisitExpression(expression.Right).AsExpression(); switch (expression.NodeType) { case ExpressionType.Equal: return(TranslateEqualityComparison(expression, lhs, rhs, expr => _hqlTreeBuilder.IsNull(expr), (l, r) => _hqlTreeBuilder.Equality(l, r))); case ExpressionType.NotEqual: return(TranslateEqualityComparison(expression, lhs, rhs, expr => _hqlTreeBuilder.IsNotNull(expr), (l, r) => _hqlTreeBuilder.Inequality(l, r))); case ExpressionType.And: return(_hqlTreeBuilder.BitwiseAnd(lhs, rhs)); case ExpressionType.AndAlso: return(_hqlTreeBuilder.BooleanAnd(lhs.AsBooleanExpression(), rhs.AsBooleanExpression())); case ExpressionType.Or: return(_hqlTreeBuilder.BitwiseOr(lhs, rhs)); case ExpressionType.OrElse: return(_hqlTreeBuilder.BooleanOr(lhs.AsBooleanExpression(), rhs.AsBooleanExpression())); case ExpressionType.Add: if (expression.Left.Type == typeof(string) && expression.Right.Type == typeof(string)) { return(_hqlTreeBuilder.MethodCall("concat", lhs, rhs)); } return(_hqlTreeBuilder.Add(lhs, rhs)); case ExpressionType.Subtract: return(_hqlTreeBuilder.Subtract(lhs, rhs)); case ExpressionType.Multiply: return(_hqlTreeBuilder.Multiply(lhs, rhs)); case ExpressionType.Divide: return(_hqlTreeBuilder.Divide(lhs, rhs)); case ExpressionType.Modulo: return(_hqlTreeBuilder.MethodCall("mod", lhs, rhs)); case ExpressionType.LessThan: return(_hqlTreeBuilder.LessThan(lhs, rhs)); case ExpressionType.LessThanOrEqual: return(_hqlTreeBuilder.LessThanOrEqual(lhs, rhs)); case ExpressionType.GreaterThan: return(_hqlTreeBuilder.GreaterThan(lhs, rhs)); case ExpressionType.GreaterThanOrEqual: return(_hqlTreeBuilder.GreaterThanOrEqual(lhs, rhs)); case ExpressionType.Coalesce: return(_hqlTreeBuilder.Coalesce(lhs, rhs)); } throw new InvalidOperationException(); }
protected HqlTreeNode VisitBinaryExpression(BinaryExpression expression) { var lhs = VisitExpression(expression.Left).AsExpression(); var rhs = VisitExpression(expression.Right).AsExpression(); switch (expression.NodeType) { case ExpressionType.Equal: // Need to check for boolean equality if (lhs is HqlBooleanExpression || rhs is HqlBooleanExpression) { lhs = _hqlTreeBuilder.Case( new [] { _hqlTreeBuilder.When(lhs, _hqlTreeBuilder.Constant(true)) }, _hqlTreeBuilder.Constant(false)); rhs = _hqlTreeBuilder.Case( new [] { _hqlTreeBuilder.When(rhs, _hqlTreeBuilder.Constant(true)) }, _hqlTreeBuilder.Constant(false)); return(_hqlTreeBuilder.Equality(lhs, rhs)); } // Check for nulls on left or right. if (expression.Right is ConstantExpression && expression.Right.Type.IsNullableOrReference() && ((ConstantExpression)expression.Right).Value == null) { return(_hqlTreeBuilder.IsNull(lhs)); } if (expression.Left is ConstantExpression && expression.Left.Type.IsNullableOrReference() && ((ConstantExpression)expression.Left).Value == null) { return(_hqlTreeBuilder.IsNull(rhs)); } // Nothing was null, use standard equality. return(_hqlTreeBuilder.Equality(lhs, rhs)); case ExpressionType.NotEqual: // Need to check for boolean in-equality if (lhs is HqlBooleanExpression || rhs is HqlBooleanExpression) { lhs = _hqlTreeBuilder.Case( new [] { _hqlTreeBuilder.When(lhs, _hqlTreeBuilder.Constant(true)) }, _hqlTreeBuilder.Constant(false)); rhs = _hqlTreeBuilder.Case( new [] { _hqlTreeBuilder.When(rhs, _hqlTreeBuilder.Constant(true)) }, _hqlTreeBuilder.Constant(false)); return(_hqlTreeBuilder.Inequality(lhs, rhs)); } // Check for nulls on left or right. if (expression.Right is ConstantExpression && expression.Right.Type.IsNullableOrReference() && ((ConstantExpression)expression.Right).Value == null) { return(_hqlTreeBuilder.IsNotNull(lhs)); } if (expression.Left is ConstantExpression && expression.Left.Type.IsNullableOrReference() && ((ConstantExpression)expression.Left).Value == null) { return(_hqlTreeBuilder.IsNotNull(rhs)); } // Nothing was null, use standard inequality. return(_hqlTreeBuilder.Inequality(lhs, rhs)); case ExpressionType.And: return(_hqlTreeBuilder.BitwiseAnd(lhs, rhs)); case ExpressionType.AndAlso: return(_hqlTreeBuilder.BooleanAnd(lhs.AsBooleanExpression(), rhs.AsBooleanExpression())); case ExpressionType.Or: return(_hqlTreeBuilder.BitwiseOr(lhs, rhs)); case ExpressionType.OrElse: return(_hqlTreeBuilder.BooleanOr(lhs.AsBooleanExpression(), rhs.AsBooleanExpression())); case ExpressionType.Add: return(_hqlTreeBuilder.Add(lhs, rhs)); case ExpressionType.Subtract: return(_hqlTreeBuilder.Subtract(lhs, rhs)); case ExpressionType.Multiply: return(_hqlTreeBuilder.Multiply(lhs, rhs)); case ExpressionType.Divide: return(_hqlTreeBuilder.Divide(lhs, rhs)); case ExpressionType.LessThan: return(_hqlTreeBuilder.LessThan(lhs, rhs)); case ExpressionType.LessThanOrEqual: return(_hqlTreeBuilder.LessThanOrEqual(lhs, rhs)); case ExpressionType.GreaterThan: return(_hqlTreeBuilder.GreaterThan(lhs, rhs)); case ExpressionType.GreaterThanOrEqual: return(_hqlTreeBuilder.GreaterThanOrEqual(lhs, rhs)); case ExpressionType.Coalesce: return(_hqlTreeBuilder.Coalesce(lhs, rhs)); } throw new InvalidOperationException(); }
public override HqlTreeNode BuildHql(MethodInfo method, Expression targetObject, ReadOnlyCollection <Expression> arguments, HqlTreeBuilder treeBuilder, IHqlExpressionVisitor visitor) { var isNull = treeBuilder.IsNull(visitor.Visit(arguments[0]).AsExpression()); return(isNull); }