DeveelDB  20151217
complete SQL database system, primarly developed for .NET/Mono frameworks
GroupOperatorHelper.cs
Go to the documentation of this file.
1 //
2 // Copyright 2010-2015 Deveel
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 // http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16 
17 using System;
18 
19 using Deveel.Data.Sql;
21 using Deveel.Data.Sql.Objects;
22 using Deveel.Data.Sql.Query;
23 using Deveel.Data.Sql.Tables;
24 using Deveel.Data.Types;
25 
26 namespace Deveel.Data {
27  static class GroupOperatorHelper {
28  private static bool IsTrue(DataObject b) {
29  return (!b.IsNull &&
30  b.Type is BooleanType &&
31  b.Value.Equals(SqlBoolean.True));
32  }
33 
34  public static DataObject EvaluateAny(SqlExpressionType plainType, DataObject ob1, DataObject ob2, EvaluateContext context) {
35  if (ob2.Type is QueryType) {
36  // The sub-query plan
37  var plan = ((SqlQueryObject)ob2.Value).QueryPlan;
38  // Discover the correlated variables for this plan.
39  var list = plan.DiscoverQueryReferences(1);
40 
41  if (list.Count > 0) {
42  // Set the correlated variables from the IVariableResolver
43  foreach (var variable in list) {
44  variable.Evaluate(context.VariableResolver);
45  }
46 
47  // Clear the cache in the context
48  context.Request.Query.ClearCachedTables();
49  }
50 
51  // Evaluate the plan,
52  var t = plan.Evaluate(context.Request);
53 
54  // The ANY operation
55  var revPlainOp = plainType.Reverse();
56  // TODO: return t.ColumnMatchesValue(0, revPlainOp, ob1);
57  throw new NotImplementedException();
58  }
59 
60  if (ob2.Type is ArrayType) {
61  var expList = (SqlArray)ob2.Value;
62  // Assume there are no matches
63  var retVal = DataObject.BooleanFalse;
64  foreach (var exp in expList) {
65  var expItem = exp.Evaluate(context);
66  if (expItem.ExpressionType != SqlExpressionType.Constant)
67  throw new InvalidOperationException();
68 
69  var evalItem = (SqlConstantExpression) expItem;
70 
71  // If null value, return null if there isn't otherwise a match found.
72  if (evalItem.Value.IsNull) {
73  retVal = DataObject.BooleanNull;
74  } else if (IsTrue(Evaluate(ob1, plainType, evalItem.Value, context))) {
75  // If there is a match, the ANY set test is true
76  return DataObject.BooleanTrue;
77  }
78  }
79  // No matches, so return either false or NULL. If there are no matches
80  // and no nulls, return false. If there are no matches and there are
81  // nulls present, return null.
82  return retVal;
83  }
84 
85  throw new InvalidOperationException("Unknown RHS of ANY.");
86  }
87 
88  public static DataObject EvaluateAll(SqlExpressionType plainType, DataObject ob1, DataObject ob2,
89  EvaluateContext context) {
90  if (ob2.Type is QueryType) {
91  // The sub-query plan
92  var planObj = (SqlQueryObject) ob2.Value;
93 
94  // Discover the correlated variables for this plan.
95  var list = planObj.QueryPlan.DiscoverQueryReferences(1);
96 
97  if (list.Count > 0) {
98  // Set the correlated variables from the IVariableResolver
99  foreach (var variable in list) {
100  variable.Evaluate(context.VariableResolver);
101  }
102 
103  // Clear the cache in the context
104  context.Request.Query.ClearCachedTables();
105  }
106 
107  // Evaluate the plan,
108  var t = planObj.QueryPlan.Evaluate(context.Request);
109 
110  var revPlainOp = plainType.Reverse();
111  return DataObject.Boolean(t.AllRowsMatchColumnValue(0, revPlainOp, ob1));
112  }
113  if (ob2.Type is ArrayType) {
114  var expList = (SqlArray) ob2.Value;
115 
116  // Assume true unless otherwise found to be false or NULL.
118  foreach (var exp in expList) {
119  var expItem = exp.Evaluate(context);
120 
121  if (expItem.ExpressionType != SqlExpressionType.Constant)
122  throw new InvalidOperationException();
123 
124  var evalItem = (SqlConstantExpression)expItem;
125 
126  // If there is a null item, we return null if not otherwise found to
127  // be false.
128  if (evalItem.Value.IsNull) {
129  retVal = DataObject.BooleanNull;
130  } else if (!IsTrue(Evaluate(ob1, plainType, evalItem.Value, context))) {
131  // If it doesn't match return false
132  return DataObject.BooleanFalse;
133  }
134  }
135 
136  // Otherwise return true or null. If all match and no NULLs return
137  // true. If all match and there are NULLs then return NULL.
138  return retVal;
139  }
140 
141  throw new InvalidOperationException("Unknown RHS of ALL.");
142  }
143 
144  private static DataObject Evaluate(DataObject left, SqlExpressionType binaryType, DataObject right, EvaluateContext context) {
145  if (binaryType.IsAll())
146  return left.Any(binaryType.SubQueryPlainType(), right, context);
147  if (binaryType.IsAny())
148  return left.All(binaryType.SubQueryPlainType(), right, context);
149 
150  switch (binaryType) {
151  case SqlExpressionType.Add:
152  return left.Add(right);
154  return left.Subtract(right);
156  return left.Multiply(right);
158  return left.Divide(right);
159  case SqlExpressionType.Modulo:
160  return left.Modulus(right);
161  case SqlExpressionType.GreaterThan:
162  return left.IsGreaterThan(right);
163  case SqlExpressionType.GreaterOrEqualThan:
164  return left.IsGreterOrEqualThan(right);
165  case SqlExpressionType.SmallerThan:
166  return left.IsSmallerThan(right);
167  case SqlExpressionType.SmallerOrEqualThan:
168  return left.IsSmallerOrEqualThan(right);
169  case SqlExpressionType.Equal:
170  return left.IsEqualTo(right);
171  case SqlExpressionType.NotEqual:
172  return left.IsNotEqualTo(right);
173  case SqlExpressionType.Is:
174  return left.Is(right);
176  return left.IsNot(right);
177  case SqlExpressionType.Like:
178  return left.IsLike(right);
179  case SqlExpressionType.NotLike:
180  return left.IsNotLike(right);
181  case SqlExpressionType.And:
182  return left.And(right);
183  case SqlExpressionType.Or:
184  return left.Or(right);
185  case SqlExpressionType.XOr:
186  return left.XOr(right);
187  // TODO: ANY and ALL
188  default:
189  throw new ExpressionEvaluateException(String.Format("The type {0} is not a binary expression or is not supported.", binaryType));
190  }
191  }
192  }
193 }
static readonly DataObject BooleanFalse
The representation of a BOOLEAN false as DataObject
Definition: DataObject.cs:44
bool IsNull
Gets a value that indicates if this object is materialized as null.
Definition: DataObject.cs:91
DataObject Multiply(DataObject other)
Definition: DataObject.cs:401
SqlType Type
Gets the SqlType that defines the object properties
Definition: DataObject.cs:78
An error occurring while evaluating an SqlExpression.
A long string in the system.
DataObject Divide(DataObject other)
Definition: DataObject.cs:410
DataObject IsLike(DataObject pattern)
When the type of this object is a string, this method verifies if the input pattern is compatible (
Definition: DataObject.cs:324
DataObject Modulus(DataObject other)
Definition: DataObject.cs:419
static readonly DataObject BooleanTrue
The representation of a BOOLEAN true as DataObject
Definition: DataObject.cs:39
static DataObject EvaluateAll(SqlExpressionType plainType, DataObject ob1, DataObject ob2, EvaluateContext context)
ISqlObject Value
Gets the underlined value that is handled.
Definition: DataObject.cs:84
static DataObject Boolean(SqlBoolean value)
Definition: DataObject.cs:544
DataObject IsSmallerThan(DataObject other)
Definition: DataObject.cs:287
SqlExpressionType
All the possible type of SqlExpression supported
IRequest Request
Gets the query in which an expression is evaluated.
DataObject IsEqualTo(DataObject other)
Compares to the given object to verify if is it equal to the current.
Definition: DataObject.cs:251
static readonly DataObject BooleanNull
The null representation of a BOOLEAN object.
Definition: DataObject.cs:49
DataObject IsNotLike(DataObject pattern)
Definition: DataObject.cs:337
DataObject IsSmallerOrEqualThan(DataObject other)
Definition: DataObject.cs:301
Represents a dynamic object that encapsulates a defined SqlType and a compatible constant ISqlObject ...
Definition: DataObject.cs:35
DataObject IsGreaterThan(DataObject other)
Definition: DataObject.cs:280
DataObject Is(DataObject other)
Compares to the given object to verify if is it compatible.
Definition: DataObject.cs:208
DataObject XOr(DataObject other)
Definition: DataObject.cs:446
static bool IsTrue(DataObject b)
DataObject IsGreterOrEqualThan(DataObject other)
Definition: DataObject.cs:294
An expression that holds a constant value.
DataObject IsNotEqualTo(DataObject other)
Compares to the given object to verify if is it not equal to the current.
Definition: DataObject.cs:273
DataObject And(DataObject other)
Definition: DataObject.cs:437
DataObject Any(SqlExpressionType type, DataObject other, EvaluateContext context)
Definition: DataObject.cs:455
An object that provides methods for accessing a finite collection of SQL expressions.
Definition: SqlArray.cs:28
static DataObject Evaluate(DataObject left, SqlExpressionType binaryType, DataObject right, EvaluateContext context)
IVariableResolver VariableResolver
Gets an object used to resolve variables from within the expression.
Encapsulates the elements needed to evaluate an SqlExpression
DataObject IsNot(DataObject other)
Compares the given object to verify if it is not compatible with this one.
Definition: DataObject.cs:232
DataObject All(SqlExpressionType type, DataObject other, EvaluateContext context)
Definition: DataObject.cs:462
DataObject Subtract(DataObject other)
Definition: DataObject.cs:392
DataObject Add(DataObject other)
Adds the given value to this object value.
Definition: DataObject.cs:383
DataObject Or(DataObject other)
Definition: DataObject.cs:428
static DataObject EvaluateAny(SqlExpressionType plainType, DataObject ob1, DataObject ob2, EvaluateContext context)