OmniSciDB  085a039ca4
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Analyzer.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2017 MapD Technologies, Inc.
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 
25 #include "Analyzer.h"
26 #include "Catalog/Catalog.h"
27 #include "Geospatial/Conversion.h"
28 #include "Geospatial/Types.h"
30 #include "RangeTableEntry.h"
31 #include "Shared/DateConverters.h"
32 #include "Shared/misc.h"
33 #include "Shared/sqltypes.h"
34 
35 #include <algorithm>
36 #include <cstring>
37 #include <iostream>
38 #include <stdexcept>
39 
40 namespace Analyzer {
41 
43  if ((type_info.is_string() || type_info.is_geometry()) && !is_null) {
44  delete constval.stringval;
45  }
46 }
47 
49  delete parsetree;
50 }
51 
53  for (auto p : rangetable) {
54  delete p;
55  }
56  delete order_by;
57  delete next_query;
58 }
59 
60 size_t Expr::get_num_column_vars(const bool include_agg) const {
61  std::set<const Analyzer::ColumnVar*,
62  bool (*)(const Analyzer::ColumnVar*, const Analyzer::ColumnVar*)>
64  collect_column_var(colvar_set, include_agg);
65  return colvar_set.size();
66 }
67 
68 std::shared_ptr<Analyzer::Expr> ColumnVar::deep_copy() const {
69  return makeExpr<ColumnVar>(type_info, table_id, column_id, rte_idx);
70 }
71 
72 void ExpressionTuple::collect_rte_idx(std::set<int>& rte_idx_set) const {
73  for (const auto& column : tuple_) {
74  column->collect_rte_idx(rte_idx_set);
75  }
76 }
77 
78 std::shared_ptr<Analyzer::Expr> ExpressionTuple::deep_copy() const {
79  std::vector<std::shared_ptr<Expr>> tuple_deep_copy;
80  for (const auto& column : tuple_) {
81  const auto column_deep_copy =
82  std::dynamic_pointer_cast<Analyzer::ColumnVar>(column->deep_copy());
83  CHECK(column_deep_copy);
84  tuple_deep_copy.push_back(column_deep_copy);
85  }
86  return makeExpr<ExpressionTuple>(tuple_deep_copy);
87 }
88 
89 std::shared_ptr<Analyzer::Expr> Var::deep_copy() const {
90  return makeExpr<Var>(type_info, table_id, column_id, rte_idx, which_row, varno);
91 }
92 
93 std::shared_ptr<Analyzer::Expr> Constant::deep_copy() const {
94  Datum d = constval;
95  if ((type_info.is_string() || type_info.is_geometry()) && !is_null) {
96  d.stringval = new std::string(*constval.stringval);
97  }
98  if (type_info.get_type() == kARRAY) {
99  return makeExpr<Constant>(type_info, is_null, value_list);
100  }
101  return makeExpr<Constant>(type_info, is_null, d);
102 }
103 
104 std::shared_ptr<Analyzer::Expr> UOper::deep_copy() const {
105  return makeExpr<UOper>(type_info, contains_agg, optype, operand->deep_copy());
106 }
107 
108 std::shared_ptr<Analyzer::Expr> BinOper::deep_copy() const {
109  return makeExpr<BinOper>(type_info,
110  contains_agg,
111  optype,
112  qualifier,
113  left_operand->deep_copy(),
114  right_operand->deep_copy());
115 }
116 
117 std::shared_ptr<Analyzer::Expr> RangeOper::deep_copy() const {
118  return makeExpr<RangeOper>(left_inclusive_,
120  left_operand_->deep_copy(),
121  right_operand_->deep_copy());
122 }
123 
124 std::shared_ptr<Analyzer::Expr> Subquery::deep_copy() const {
125  // not supported yet.
126  CHECK(false);
127  return nullptr;
128 }
129 
130 std::shared_ptr<Analyzer::Expr> InValues::deep_copy() const {
131  std::list<std::shared_ptr<Analyzer::Expr>> new_value_list;
132  for (auto p : value_list) {
133  new_value_list.push_back(p->deep_copy());
134  }
135  return makeExpr<InValues>(arg->deep_copy(), new_value_list);
136 }
137 
138 std::shared_ptr<Analyzer::Expr> CharLengthExpr::deep_copy() const {
139  return makeExpr<CharLengthExpr>(arg->deep_copy(), calc_encoded_length);
140 }
141 
142 std::shared_ptr<Analyzer::Expr> KeyForStringExpr::deep_copy() const {
143  return makeExpr<KeyForStringExpr>(arg->deep_copy());
144 }
145 
146 std::shared_ptr<Analyzer::Expr> SampleRatioExpr::deep_copy() const {
147  return makeExpr<SampleRatioExpr>(arg->deep_copy());
148 }
149 
150 std::shared_ptr<Analyzer::Expr> CardinalityExpr::deep_copy() const {
151  return makeExpr<CardinalityExpr>(arg->deep_copy());
152 }
153 
154 std::shared_ptr<Analyzer::Expr> LikeExpr::deep_copy() const {
155  return makeExpr<LikeExpr>(arg->deep_copy(),
156  like_expr->deep_copy(),
157  escape_expr ? escape_expr->deep_copy() : nullptr,
158  is_ilike,
159  is_simple);
160 }
161 
162 std::shared_ptr<Analyzer::Expr> RegexpExpr::deep_copy() const {
163  return makeExpr<RegexpExpr>(arg->deep_copy(),
164  pattern_expr->deep_copy(),
165  escape_expr ? escape_expr->deep_copy() : nullptr);
166 }
167 
168 std::shared_ptr<Analyzer::Expr> WidthBucketExpr::deep_copy() const {
169  return makeExpr<WidthBucketExpr>(target_value_->deep_copy(),
170  lower_bound_->deep_copy(),
171  upper_bound_->deep_copy(),
172  partition_count_->deep_copy());
173 }
174 
175 std::shared_ptr<Analyzer::Expr> LikelihoodExpr::deep_copy() const {
176  return makeExpr<LikelihoodExpr>(arg->deep_copy(), likelihood);
177 }
178 
179 std::shared_ptr<Analyzer::Expr> AggExpr::deep_copy() const {
180  return makeExpr<AggExpr>(
181  type_info, aggtype, arg ? arg->deep_copy() : nullptr, is_distinct, arg1);
182 }
183 
184 std::shared_ptr<Analyzer::Expr> CaseExpr::deep_copy() const {
185  std::list<std::pair<std::shared_ptr<Analyzer::Expr>, std::shared_ptr<Analyzer::Expr>>>
186  new_list;
187  for (auto p : expr_pair_list) {
188  new_list.emplace_back(p.first->deep_copy(), p.second->deep_copy());
189  }
190  return makeExpr<CaseExpr>(type_info,
191  contains_agg,
192  new_list,
193  else_expr == nullptr ? nullptr : else_expr->deep_copy());
194 }
195 
196 std::shared_ptr<Analyzer::Expr> ExtractExpr::deep_copy() const {
197  return makeExpr<ExtractExpr>(type_info, contains_agg, field_, from_expr_->deep_copy());
198 }
199 
200 std::shared_ptr<Analyzer::Expr> DateaddExpr::deep_copy() const {
201  return makeExpr<DateaddExpr>(
202  type_info, field_, number_->deep_copy(), datetime_->deep_copy());
203 }
204 
205 std::shared_ptr<Analyzer::Expr> DatediffExpr::deep_copy() const {
206  return makeExpr<DatediffExpr>(
207  type_info, field_, start_->deep_copy(), end_->deep_copy());
208 }
209 
210 std::shared_ptr<Analyzer::Expr> DatetruncExpr::deep_copy() const {
211  return makeExpr<DatetruncExpr>(
212  type_info, contains_agg, field_, from_expr_->deep_copy());
213 }
214 
215 std::shared_ptr<Analyzer::Expr> OffsetInFragment::deep_copy() const {
216  return makeExpr<OffsetInFragment>();
217 }
218 
219 std::shared_ptr<Analyzer::Expr> WindowFunction::deep_copy() const {
220  return makeExpr<WindowFunction>(
222 }
223 
225  return makeExpr<Analyzer::ArrayExpr>(
227 }
228 
229 std::shared_ptr<Analyzer::Expr> GeoUOper::deep_copy() const {
231  return makeExpr<GeoUOper>(op_, type_info, type_info, args0_);
232  }
233  return makeExpr<GeoUOper>(op_, type_info, ti0_, args0_);
234 }
235 
236 std::shared_ptr<Analyzer::Expr> GeoBinOper::deep_copy() const {
237  return makeExpr<GeoBinOper>(op_, type_info, ti0_, ti1_, args0_, args1_);
238 }
239 
241  const SQLTypeInfo& left_type,
242  const SQLTypeInfo& right_type,
243  SQLTypeInfo* new_left_type,
244  SQLTypeInfo* new_right_type) {
245  SQLTypeInfo result_type;
246  SQLTypeInfo common_type;
247  *new_left_type = left_type;
248  *new_right_type = right_type;
249  if (IS_LOGIC(op)) {
250  if (left_type.get_type() != kBOOLEAN || right_type.get_type() != kBOOLEAN) {
251  throw std::runtime_error(
252  "non-boolean operands cannot be used in logic operations.");
253  }
254  result_type = SQLTypeInfo(kBOOLEAN, false);
255  } else if (IS_COMPARISON(op)) {
256  if (left_type != right_type) {
257  if (left_type.is_number() && right_type.is_number()) {
258  common_type = common_numeric_type(left_type, right_type);
259  *new_left_type = common_type;
260  new_left_type->set_notnull(left_type.get_notnull());
261  *new_right_type = common_type;
262  new_right_type->set_notnull(right_type.get_notnull());
263  } else if (left_type.is_time() && right_type.is_time()) {
264  switch (left_type.get_type()) {
265  case kTIMESTAMP:
266  switch (right_type.get_type()) {
267  case kTIME:
268  throw std::runtime_error("Cannont compare between TIMESTAMP and TIME.");
269  break;
270  case kDATE:
271  *new_left_type = SQLTypeInfo(left_type.get_type(),
272  left_type.get_dimension(),
273  0,
274  left_type.get_notnull());
275  *new_right_type = *new_left_type;
276  new_right_type->set_notnull(right_type.get_notnull());
277  break;
278  case kTIMESTAMP:
279  *new_left_type = SQLTypeInfo(
280  kTIMESTAMP,
281  std::max(left_type.get_dimension(), right_type.get_dimension()),
282  0,
283  left_type.get_notnull());
284  *new_right_type = SQLTypeInfo(
285  kTIMESTAMP,
286  std::max(left_type.get_dimension(), right_type.get_dimension()),
287  0,
288  right_type.get_notnull());
289  break;
290  default:
291  CHECK(false);
292  }
293  break;
294  case kTIME:
295  switch (right_type.get_type()) {
296  case kTIMESTAMP:
297  throw std::runtime_error("Cannont compare between TIME and TIMESTAMP.");
298  break;
299  case kDATE:
300  throw std::runtime_error("Cannont compare between TIME and DATE.");
301  break;
302  case kTIME:
303  *new_left_type = SQLTypeInfo(
304  kTIME,
305  std::max(left_type.get_dimension(), right_type.get_dimension()),
306  0,
307  left_type.get_notnull());
308  *new_right_type = SQLTypeInfo(
309  kTIME,
310  std::max(left_type.get_dimension(), right_type.get_dimension()),
311  0,
312  right_type.get_notnull());
313  break;
314  default:
315  CHECK(false);
316  }
317  break;
318  case kDATE:
319  switch (right_type.get_type()) {
320  case kTIMESTAMP:
321  *new_left_type = SQLTypeInfo(right_type.get_type(),
322  right_type.get_dimension(),
323  0,
324  left_type.get_notnull());
325  *new_right_type = *new_left_type;
326  new_right_type->set_notnull(right_type.get_notnull());
327  break;
328  case kDATE:
329  *new_left_type = SQLTypeInfo(left_type.get_type(),
330  left_type.get_dimension(),
331  0,
332  left_type.get_notnull());
333  *new_right_type = *new_left_type;
334  new_right_type->set_notnull(right_type.get_notnull());
335  break;
336  case kTIME:
337  throw std::runtime_error("Cannont compare between DATE and TIME.");
338  break;
339  default:
340  CHECK(false);
341  }
342  break;
343  default:
344  CHECK(false);
345  }
346  } else if (left_type.is_string() && right_type.is_time()) {
347  *new_left_type = right_type;
348  new_left_type->set_notnull(left_type.get_notnull());
349  *new_right_type = right_type;
350  } else if (left_type.is_time() && right_type.is_string()) {
351  *new_left_type = left_type;
352  *new_right_type = left_type;
353  new_right_type->set_notnull(right_type.get_notnull());
354  } else if (left_type.is_string() && right_type.is_string()) {
355  *new_left_type = left_type;
356  *new_right_type = right_type;
357  } else if (left_type.is_boolean() && right_type.is_boolean()) {
358  const bool notnull = left_type.get_notnull() && right_type.get_notnull();
359  common_type = SQLTypeInfo(kBOOLEAN, notnull);
360  *new_left_type = common_type;
361  *new_right_type = common_type;
362  } else {
363  throw std::runtime_error("Cannot compare between " + left_type.get_type_name() +
364  " and " + right_type.get_type_name());
365  }
366  }
367  result_type = SQLTypeInfo(kBOOLEAN, false);
368  } else if (op == kMINUS &&
369  (left_type.get_type() == kDATE || left_type.get_type() == kTIMESTAMP) &&
370  right_type.is_timeinterval()) {
371  *new_left_type = left_type;
372  *new_right_type = right_type;
373  result_type = left_type;
374  } else if (IS_ARITHMETIC(op)) {
375  if (!(left_type.is_number() || left_type.is_timeinterval()) ||
376  !(right_type.is_number() || right_type.is_timeinterval())) {
377  throw std::runtime_error("non-numeric operands in arithmetic operations.");
378  }
379  if (op == kMODULO && (!left_type.is_integer() || !right_type.is_integer())) {
380  throw std::runtime_error("non-integer operands in modulo operation.");
381  }
382  common_type = common_numeric_type(left_type, right_type);
383  if (common_type.is_decimal()) {
384  if (op == kMULTIPLY) {
385  // Decimal multiplication requires common_type adjustment:
386  // dimension and scale of the result should be increased.
387  auto new_dimension = left_type.get_dimension() + right_type.get_dimension();
388  // If new dimension is over 20 digits, the result may overflow, or it may not.
389  // Rely on the runtime overflow detection rather than a static check here.
390  if (common_type.get_dimension() < new_dimension) {
391  common_type.set_dimension(new_dimension);
392  }
393  common_type.set_scale(left_type.get_scale() + right_type.get_scale());
394  } else if (op == kPLUS || op == kMINUS) {
395  // Scale should remain the same but dimension could actually go up
396  common_type.set_dimension(common_type.get_dimension() + 1);
397  }
398  }
399  *new_left_type = common_type;
400  new_left_type->set_notnull(left_type.get_notnull());
401  *new_right_type = common_type;
402  new_right_type->set_notnull(right_type.get_notnull());
403  if (op == kMULTIPLY) {
404  new_left_type->set_scale(left_type.get_scale());
405  new_right_type->set_scale(right_type.get_scale());
406  }
407  result_type = common_type;
408  } else {
409  throw std::runtime_error("invalid binary operator type.");
410  }
411  result_type.set_notnull(left_type.get_notnull() && right_type.get_notnull());
412  return result_type;
413 }
414 
416  const SQLTypeInfo& type2) {
417  SQLTypeInfo common_type;
419  int comp_param = 0;
420  CHECK(type1.is_string() && type2.is_string());
421  // if type1 and type2 have the same DICT encoding then keep it
422  // otherwise, they must be decompressed
423  if (type1.get_compression() == kENCODING_DICT &&
424  type2.get_compression() == kENCODING_DICT) {
425  if (type1.get_comp_param() == type2.get_comp_param() ||
426  type1.get_comp_param() == TRANSIENT_DICT(type2.get_comp_param())) {
427  comp = kENCODING_DICT;
428  comp_param = std::min(type1.get_comp_param(), type2.get_comp_param());
429  }
430  } else if (type1.get_compression() == kENCODING_DICT &&
431  type2.get_compression() == kENCODING_NONE) {
432  comp_param = type1.get_comp_param();
433  } else if (type1.get_compression() == kENCODING_NONE &&
434  type2.get_compression() == kENCODING_DICT) {
435  comp_param = type2.get_comp_param();
436  } else {
437  comp_param = std::max(type1.get_comp_param(),
438  type2.get_comp_param()); // preserve previous comp_param if set
439  }
440  const bool notnull = type1.get_notnull() && type2.get_notnull();
441  if (type1.get_type() == kTEXT || type2.get_type() == kTEXT) {
442  common_type = SQLTypeInfo(kTEXT, 0, 0, notnull, comp, comp_param, kNULLT);
443  return common_type;
444  }
445  common_type = SQLTypeInfo(kVARCHAR,
446  std::max(type1.get_dimension(), type2.get_dimension()),
447  0,
448  notnull,
449  comp,
450  comp_param,
451  kNULLT);
452  return common_type;
453 }
454 
456  const SQLTypeInfo& type2) {
457  SQLTypeInfo common_type;
458  const bool notnull = type1.get_notnull() && type2.get_notnull();
459  if (type1.get_type() == type2.get_type()) {
460  CHECK(((type1.is_number() || type1.is_timeinterval()) &&
461  (type2.is_number() || type2.is_timeinterval())) ||
462  (type1.is_boolean() && type2.is_boolean()));
463  common_type = SQLTypeInfo(type1.get_type(),
464  std::max(type1.get_dimension(), type2.get_dimension()),
465  std::max(type1.get_scale(), type2.get_scale()),
466  notnull);
467  return common_type;
468  }
469  std::string timeinterval_op_error{
470  "Operator type not supported for time interval arithmetic: "};
471  if (type1.is_timeinterval()) {
472  if (!type2.is_integer()) {
473  throw std::runtime_error(timeinterval_op_error + type2.get_type_name());
474  }
475  return type1;
476  }
477  if (type2.is_timeinterval()) {
478  if (!type1.is_integer()) {
479  throw std::runtime_error(timeinterval_op_error + type1.get_type_name());
480  }
481  return type2;
482  }
483  CHECK(type1.is_number() && type2.is_number());
484  switch (type1.get_type()) {
485  case kTINYINT:
486  switch (type2.get_type()) {
487  case kSMALLINT:
488  common_type = SQLTypeInfo(kSMALLINT, notnull);
489  break;
490  case kINT:
491  common_type = SQLTypeInfo(kINT, notnull);
492  break;
493  case kBIGINT:
494  common_type = SQLTypeInfo(kBIGINT, notnull);
495  break;
496  case kFLOAT:
497  common_type = SQLTypeInfo(kFLOAT, notnull);
498  break;
499  case kDOUBLE:
500  common_type = SQLTypeInfo(kDOUBLE, notnull);
501  break;
502  case kNUMERIC:
503  case kDECIMAL:
504  common_type =
506  std::max(5 + type2.get_scale(), type2.get_dimension()),
507  type2.get_scale(),
508  notnull);
509  break;
510  default:
511  CHECK(false);
512  }
513  break;
514  case kSMALLINT:
515  switch (type2.get_type()) {
516  case kTINYINT:
517  common_type = SQLTypeInfo(kSMALLINT, notnull);
518  break;
519  case kINT:
520  common_type = SQLTypeInfo(kINT, notnull);
521  break;
522  case kBIGINT:
523  common_type = SQLTypeInfo(kBIGINT, notnull);
524  break;
525  case kFLOAT:
526  common_type = SQLTypeInfo(kFLOAT, notnull);
527  break;
528  case kDOUBLE:
529  common_type = SQLTypeInfo(kDOUBLE, notnull);
530  break;
531  case kNUMERIC:
532  case kDECIMAL:
533  common_type =
535  std::max(5 + type2.get_scale(), type2.get_dimension()),
536  type2.get_scale(),
537  notnull);
538  break;
539  default:
540  CHECK(false);
541  }
542  break;
543  case kINT:
544  switch (type2.get_type()) {
545  case kTINYINT:
546  common_type = SQLTypeInfo(kINT, notnull);
547  break;
548  case kSMALLINT:
549  common_type = SQLTypeInfo(kINT, notnull);
550  break;
551  case kBIGINT:
552  common_type = SQLTypeInfo(kBIGINT, notnull);
553  break;
554  case kFLOAT:
555  common_type = SQLTypeInfo(kFLOAT, notnull);
556  break;
557  case kDOUBLE:
558  common_type = SQLTypeInfo(kDOUBLE, notnull);
559  break;
560  case kNUMERIC:
561  case kDECIMAL:
562  common_type = SQLTypeInfo(
563  kDECIMAL,
564  std::max(std::min(19, 10 + type2.get_scale()), type2.get_dimension()),
565  type2.get_scale(),
566  notnull);
567  break;
568  default:
569  CHECK(false);
570  }
571  break;
572  case kBIGINT:
573  switch (type2.get_type()) {
574  case kTINYINT:
575  common_type = SQLTypeInfo(kBIGINT, notnull);
576  break;
577  case kSMALLINT:
578  common_type = SQLTypeInfo(kBIGINT, notnull);
579  break;
580  case kINT:
581  common_type = SQLTypeInfo(kBIGINT, notnull);
582  break;
583  case kFLOAT:
584  common_type = SQLTypeInfo(kFLOAT, notnull);
585  break;
586  case kDOUBLE:
587  common_type = SQLTypeInfo(kDOUBLE, notnull);
588  break;
589  case kNUMERIC:
590  case kDECIMAL:
591  common_type = SQLTypeInfo(kDECIMAL, 19, type2.get_scale(), notnull);
592  break;
593  default:
594  CHECK(false);
595  }
596  break;
597  case kFLOAT:
598  switch (type2.get_type()) {
599  case kTINYINT:
600  common_type = SQLTypeInfo(kFLOAT, notnull);
601  break;
602  case kSMALLINT:
603  common_type = SQLTypeInfo(kFLOAT, notnull);
604  break;
605  case kINT:
606  common_type = SQLTypeInfo(kFLOAT, notnull);
607  break;
608  case kBIGINT:
609  common_type = SQLTypeInfo(kFLOAT, notnull);
610  break;
611  case kDOUBLE:
612  common_type = SQLTypeInfo(kDOUBLE, notnull);
613  break;
614  case kNUMERIC:
615  case kDECIMAL:
616  common_type = SQLTypeInfo(kFLOAT, notnull);
617  break;
618  default:
619  CHECK(false);
620  }
621  break;
622  case kDOUBLE:
623  switch (type2.get_type()) {
624  case kTINYINT:
625  case kSMALLINT:
626  case kINT:
627  case kBIGINT:
628  case kFLOAT:
629  case kNUMERIC:
630  case kDECIMAL:
631  common_type = SQLTypeInfo(kDOUBLE, notnull);
632  break;
633  default:
634  CHECK(false);
635  }
636  break;
637  case kNUMERIC:
638  case kDECIMAL:
639  switch (type2.get_type()) {
640  case kTINYINT:
641  common_type =
643  std::max(3 + type1.get_scale(), type1.get_dimension()),
644  type1.get_scale(),
645  notnull);
646  break;
647  case kSMALLINT:
648  common_type =
650  std::max(5 + type1.get_scale(), type1.get_dimension()),
651  type1.get_scale(),
652  notnull);
653  break;
654  case kINT:
655  common_type = SQLTypeInfo(
656  kDECIMAL,
657  std::max(std::min(19, 10 + type1.get_scale()), type2.get_dimension()),
658  type1.get_scale(),
659  notnull);
660  break;
661  case kBIGINT:
662  common_type = SQLTypeInfo(kDECIMAL, 19, type1.get_scale(), notnull);
663  break;
664  case kFLOAT:
665  common_type = SQLTypeInfo(kFLOAT, notnull);
666  break;
667  case kDOUBLE:
668  common_type = SQLTypeInfo(kDOUBLE, notnull);
669  break;
670  case kNUMERIC:
671  case kDECIMAL: {
672  int common_scale = std::max(type1.get_scale(), type2.get_scale());
673  common_type = SQLTypeInfo(kDECIMAL,
674  std::max(type1.get_dimension() - type1.get_scale(),
675  type2.get_dimension() - type2.get_scale()) +
676  common_scale,
677  common_scale,
678  notnull);
679  break;
680  }
681  default:
682  CHECK(false);
683  }
684  break;
685  default:
686  CHECK(false);
687  }
688  common_type.set_fixed_size();
689  return common_type;
690 }
691 
692 std::shared_ptr<Analyzer::Expr> Expr::decompress() {
694  return shared_from_this();
695  }
696  SQLTypeInfo new_type_info(type_info.get_type(),
701  0,
703  return makeExpr<UOper>(new_type_info, contains_agg, kCAST, shared_from_this());
704 }
705 
706 std::shared_ptr<Analyzer::Expr> Expr::add_cast(const SQLTypeInfo& new_type_info) {
707  if (new_type_info == type_info) {
708  return shared_from_this();
709  }
710  if (new_type_info.is_string() && type_info.is_string() &&
711  new_type_info.get_compression() == kENCODING_DICT &&
713  (new_type_info.get_comp_param() == type_info.get_comp_param() ||
714  new_type_info.get_comp_param() == TRANSIENT_DICT(type_info.get_comp_param()))) {
715  return shared_from_this();
716  }
717  if (!type_info.is_castable(new_type_info)) {
718  throw std::runtime_error("Cannot CAST from " + type_info.get_type_name() + " to " +
719  new_type_info.get_type_name());
720  }
721  // @TODO(wei) temporary restriction until executor can support this.
722  const bool has_non_literal_operands = get_num_column_vars(true) > 0UL;
723  if (has_non_literal_operands && new_type_info.is_string() &&
724  new_type_info.get_compression() == kENCODING_DICT &&
725  new_type_info.get_comp_param() <= TRANSIENT_DICT_ID) {
727  throw std::runtime_error(
728  "Implict casts of TEXT ENCODING NONE to TEXT ENCODED DICT are not allowed "
729  "for non-literal arguments. Consider adding an explicit conversion to a "
730  "dictionary-encoded text type with ENCODE_TEXT(<none-encoded text arg>).");
731  }
732  throw std::runtime_error(
733  "Internal error: Cannot apply transient dictionary encoding "
734  "to non-literal expression.");
735  }
736  return makeExpr<UOper>(new_type_info, contains_agg, kCAST, shared_from_this());
737 }
738 
739 namespace {
740 
741 // Return dec * 10^-scale
742 template <typename T>
743 T floatFromDecimal(int64_t const dec, unsigned const scale) {
744  static_assert(std::is_floating_point_v<T>);
745  return static_cast<T>(dec) / shared::power10(scale);
746 }
747 
748 // Q: Why is there a maxRound() but no minRound()?
749 // A: The numerical value of std::numeric_limits<int64_t>::min() is unchanged when cast
750 // to either float or double, but std::numeric_limits<intXX_t>::max() is incremented to
751 // 2^(XX-1) when cast to float/double for XX in {32,64}, which is an invalid intXX_t
752 // value. Thus the maximum float/double that can be cast to a valid integer type must be
753 // calculated directly, and not just compared to std::numeric_limits<intXX_t>::max().
754 template <typename FLOAT_TYPE, typename INT_TYPE>
755 constexpr FLOAT_TYPE maxRound() {
756  static_assert(std::is_integral_v<INT_TYPE> && std::is_floating_point_v<FLOAT_TYPE>);
757  constexpr int dd =
758  std::numeric_limits<INT_TYPE>::digits - std::numeric_limits<FLOAT_TYPE>::digits;
759  if constexpr (0 < dd) { // NOLINT
760  return static_cast<FLOAT_TYPE>(std::numeric_limits<INT_TYPE>::max() - (1ll << dd));
761  } else {
762  return static_cast<FLOAT_TYPE>(std::numeric_limits<INT_TYPE>::max());
763  }
764 }
765 
766 template <typename TO, typename FROM>
767 TO safeNarrow(FROM const from) {
768  static_assert(std::is_integral_v<TO> && std::is_integral_v<FROM>);
769  static_assert(sizeof(TO) < sizeof(FROM));
770  if (from < static_cast<FROM>(std::numeric_limits<TO>::min()) ||
771  static_cast<FROM>(std::numeric_limits<TO>::max()) < from) {
772  throw std::runtime_error("Overflow or underflow");
773  }
774  return static_cast<TO>(from);
775 }
776 
777 template <typename T>
778 T roundDecimal(int64_t n, unsigned scale) {
779  static_assert(std::is_integral_v<T>);
780  constexpr size_t max_scale = std::numeric_limits<uint64_t>::digits10; // 19
781  constexpr auto pow10 = shared::powersOf<uint64_t, max_scale + 1>(10);
782  if (scale == 0) {
783  if constexpr (sizeof(T) < sizeof(int64_t)) { // NOLINT
784  return safeNarrow<T>(n);
785  } else {
786  return n;
787  }
788  } else if (max_scale < scale) {
789  return 0; // 0.09223372036854775807 rounds to 0
790  }
791  uint64_t const u = std::abs(n);
792  uint64_t const pow = pow10[scale];
793  uint64_t div = u / pow;
794  uint64_t rem = u % pow;
795  div += pow / 2 <= rem;
796  if constexpr (sizeof(T) < sizeof(int64_t)) { // NOLINT
797  return safeNarrow<T>(static_cast<int64_t>(n < 0 ? -div : div));
798  } else {
799  return n < 0 ? -div : div;
800  }
801 }
802 
803 template <typename TO, typename FROM>
804 TO safeRound(FROM const from) {
805  static_assert(std::is_integral_v<TO> && std::is_floating_point_v<FROM>);
806  constexpr FROM max_float = maxRound<FROM, TO>();
807  FROM const n = std::round(from);
808  if (n < static_cast<FROM>(std::numeric_limits<TO>::min()) || max_float < n) {
809  throw std::runtime_error("Overflow or underflow");
810  }
811  return static_cast<TO>(n);
812 }
813 
814 // Return numeric/decimal representation of from with given scale.
815 template <typename T>
816 int64_t safeScale(T from, unsigned const scale) {
817  static_assert(std::is_arithmetic_v<T>);
818  constexpr size_t max_scale = std::numeric_limits<int64_t>::digits10; // 18
819  constexpr auto pow10 = shared::powersOf<int64_t, max_scale + 1>(10);
820  if constexpr (std::is_integral_v<T>) { // NOLINT
821  int64_t retval;
822  if (scale < pow10.size()) {
823 #ifdef __linux__
824  if (!__builtin_mul_overflow(from, pow10[scale], &retval)) {
825  return retval;
826  }
827  // Not over flow safe.
828 #else
829  return from * pow10[scale];
830 #endif
831  }
832  } else if constexpr (std::is_floating_point_v<T>) {
833  if (scale < pow10.size()) {
834  return safeRound<int64_t>(from * pow10[scale]);
835  }
836  }
837  if (from == 0) {
838  return 0;
839  }
840  throw std::runtime_error("Overflow or underflow");
841 }
842 
843 } // namespace
844 
845 void Constant::cast_number(const SQLTypeInfo& new_type_info) {
846  switch (type_info.get_type()) {
847  case kTINYINT:
848  switch (new_type_info.get_type()) {
849  case kTINYINT:
850  break;
851  case kINT:
852  constval.intval = (int32_t)constval.tinyintval;
853  break;
854  case kSMALLINT:
856  break;
857  case kBIGINT:
858  case kTIMESTAMP:
860  break;
861  case kDOUBLE:
863  break;
864  case kFLOAT:
866  break;
867  case kNUMERIC:
868  case kDECIMAL:
870  break;
871  default:
872  CHECK(false);
873  }
874  break;
875  case kINT:
876  switch (new_type_info.get_type()) {
877  case kTINYINT:
878  constval.tinyintval = safeNarrow<int8_t>(constval.intval);
879  break;
880  case kINT:
881  break;
882  case kSMALLINT:
883  constval.smallintval = safeNarrow<int16_t>(constval.intval);
884  break;
885  case kBIGINT:
886  case kTIMESTAMP:
887  constval.bigintval = (int64_t)constval.intval;
888  break;
889  case kDOUBLE:
890  constval.doubleval = (double)constval.intval;
891  break;
892  case kFLOAT:
893  constval.floatval = (float)constval.intval;
894  break;
895  case kNUMERIC:
896  case kDECIMAL:
897  constval.bigintval = safeScale(constval.intval, new_type_info.get_scale());
898  break;
899  default:
900  CHECK(false);
901  }
902  break;
903  case kSMALLINT:
904  switch (new_type_info.get_type()) {
905  case kTINYINT:
906  constval.tinyintval = safeNarrow<int8_t>(constval.smallintval);
907  break;
908  case kINT:
909  constval.intval = (int32_t)constval.smallintval;
910  break;
911  case kSMALLINT:
912  break;
913  case kBIGINT:
914  case kTIMESTAMP:
916  break;
917  case kDOUBLE:
919  break;
920  case kFLOAT:
922  break;
923  case kNUMERIC:
924  case kDECIMAL:
926  break;
927  default:
928  CHECK(false);
929  }
930  break;
931  case kBIGINT:
932  switch (new_type_info.get_type()) {
933  case kTINYINT:
934  constval.tinyintval = safeNarrow<int8_t>(constval.bigintval);
935  break;
936  case kINT:
937  constval.intval = safeNarrow<int32_t>(constval.bigintval);
938  break;
939  case kSMALLINT:
940  constval.smallintval = safeNarrow<int16_t>(constval.bigintval);
941  break;
942  case kBIGINT:
943  case kTIMESTAMP:
944  break;
945  case kDOUBLE:
947  break;
948  case kFLOAT:
950  break;
951  case kNUMERIC:
952  case kDECIMAL:
954  break;
955  default:
956  CHECK(false);
957  }
958  break;
959  case kDOUBLE:
960  switch (new_type_info.get_type()) {
961  case kTINYINT:
962  constval.tinyintval = safeRound<int8_t>(constval.doubleval);
963  break;
964  case kINT:
965  constval.intval = safeRound<int32_t>(constval.doubleval);
966  break;
967  case kSMALLINT:
968  constval.smallintval = safeRound<int16_t>(constval.doubleval);
969  break;
970  case kBIGINT:
971  case kTIMESTAMP:
972  constval.bigintval = safeRound<int64_t>(constval.doubleval);
973  break;
974  case kDOUBLE:
975  break;
976  case kFLOAT:
978  break;
979  case kNUMERIC:
980  case kDECIMAL:
982  break;
983  default:
984  CHECK(false);
985  }
986  break;
987  case kFLOAT:
988  switch (new_type_info.get_type()) {
989  case kTINYINT:
990  constval.tinyintval = safeRound<int8_t>(constval.floatval);
991  break;
992  case kINT:
993  constval.intval = safeRound<int32_t>(constval.floatval);
994  break;
995  case kSMALLINT:
996  constval.smallintval = safeRound<int16_t>(constval.floatval);
997  break;
998  case kBIGINT:
999  case kTIMESTAMP:
1000  constval.bigintval = safeRound<int64_t>(constval.floatval);
1001  break;
1002  case kDOUBLE:
1003  constval.doubleval = (double)constval.floatval;
1004  break;
1005  case kFLOAT:
1006  break;
1007  case kNUMERIC:
1008  case kDECIMAL:
1009  constval.bigintval = safeScale(constval.floatval, new_type_info.get_scale());
1010  break;
1011  default:
1012  CHECK(false);
1013  }
1014  break;
1015  case kNUMERIC:
1016  case kDECIMAL:
1017  switch (new_type_info.get_type()) {
1018  case kTINYINT:
1020  roundDecimal<int8_t>(constval.bigintval, type_info.get_scale());
1021  break;
1022  case kINT:
1023  constval.intval =
1024  roundDecimal<int32_t>(constval.bigintval, type_info.get_scale());
1025  break;
1026  case kSMALLINT:
1028  roundDecimal<int16_t>(constval.bigintval, type_info.get_scale());
1029  break;
1030  case kBIGINT:
1031  case kTIMESTAMP:
1033  roundDecimal<int64_t>(constval.bigintval, type_info.get_scale());
1034  break;
1035  case kDOUBLE:
1037  floatFromDecimal<double>(constval.bigintval, type_info.get_scale());
1038  break;
1039  case kFLOAT:
1040  constval.floatval =
1041  floatFromDecimal<float>(constval.bigintval, type_info.get_scale());
1042  break;
1043  case kNUMERIC:
1044  case kDECIMAL:
1046  constval.bigintval, type_info, new_type_info);
1047  break;
1048  default:
1049  CHECK(false);
1050  }
1051  break;
1052  case kTIMESTAMP:
1053  switch (new_type_info.get_type()) {
1054  case kTINYINT:
1055  constval.tinyintval = safeNarrow<int8_t>(constval.bigintval);
1056  break;
1057  case kINT:
1058  constval.intval = safeNarrow<int32_t>(constval.bigintval);
1059  break;
1060  case kSMALLINT:
1061  constval.smallintval = safeNarrow<int16_t>(constval.bigintval);
1062  break;
1063  case kBIGINT:
1064  case kTIMESTAMP:
1065  break;
1066  case kDOUBLE:
1067  constval.doubleval = static_cast<double>(constval.bigintval);
1068  break;
1069  case kFLOAT:
1070  constval.floatval = static_cast<float>(constval.bigintval);
1071  break;
1072  case kNUMERIC:
1073  case kDECIMAL:
1074  for (int i = 0; i < new_type_info.get_scale(); i++) {
1075  constval.bigintval *= 10;
1076  }
1077  break;
1078  default:
1079  CHECK(false);
1080  }
1081  break;
1082  case kBOOLEAN:
1083  switch (new_type_info.get_type()) {
1084  case kTINYINT:
1085  constval.tinyintval = constval.boolval ? 1 : 0;
1086  break;
1087  case kINT:
1088  constval.intval = constval.boolval ? 1 : 0;
1089  break;
1090  case kSMALLINT:
1092  break;
1093  case kBIGINT:
1094  case kTIMESTAMP:
1095  constval.bigintval = constval.boolval ? 1 : 0;
1096  break;
1097  case kDOUBLE:
1098  constval.doubleval = constval.boolval ? 1 : 0;
1099  break;
1100  case kFLOAT:
1101  constval.floatval = constval.boolval ? 1 : 0;
1102  break;
1103  case kNUMERIC:
1104  case kDECIMAL:
1105  constval.bigintval = constval.boolval ? 1 : 0;
1106  for (int i = 0; i < new_type_info.get_scale(); i++) {
1107  constval.bigintval *= 10;
1108  }
1109  break;
1110  default:
1111  CHECK(false);
1112  }
1113  break;
1114  default:
1115  CHECK(false);
1116  }
1117  type_info = new_type_info;
1118 }
1119 
1120 void Constant::cast_string(const SQLTypeInfo& new_type_info) {
1121  std::string* s = constval.stringval;
1122  if (s != nullptr && new_type_info.get_type() != kTEXT &&
1123  static_cast<size_t>(new_type_info.get_dimension()) < s->length()) {
1124  // truncate string
1125  constval.stringval = new std::string(s->substr(0, new_type_info.get_dimension()));
1126  delete s;
1127  }
1128  type_info = new_type_info;
1129 }
1130 
1131 void Constant::cast_from_string(const SQLTypeInfo& new_type_info) {
1132  std::string* s = constval.stringval;
1133  SQLTypeInfo ti = new_type_info;
1134  constval = StringToDatum(*s, ti);
1135  delete s;
1136  type_info = new_type_info;
1137 }
1138 
1139 void Constant::cast_to_string(const SQLTypeInfo& str_type_info) {
1140  const auto str_val = DatumToString(constval, type_info);
1141  constval.stringval = new std::string(str_val);
1142  if (str_type_info.get_type() != kTEXT &&
1143  constval.stringval->length() > static_cast<size_t>(str_type_info.get_dimension())) {
1144  // truncate the string
1145  *constval.stringval = constval.stringval->substr(0, str_type_info.get_dimension());
1146  }
1147  type_info = str_type_info;
1148 }
1149 
1150 namespace {
1151 
1152 // TODO(adb): we should revisit this, as one could argue a Datum should never contain
1153 // a null sentinel. In fact, if we bundle Datum with a null boolean ("NullableDatum"),
1154 // the logic becomes more explicit. There are likely other bugs associated with the
1155 // current logic -- for example, boolean is set to -128 which is likely UB
1156 inline bool is_null_value(const SQLTypeInfo& ti, const Datum& constval) {
1157  switch (ti.get_type()) {
1158  case kBOOLEAN:
1159  return constval.tinyintval == NULL_BOOLEAN;
1160  case kTINYINT:
1161  return constval.tinyintval == NULL_TINYINT;
1162  case kINT:
1163  return constval.intval == NULL_INT;
1164  case kSMALLINT:
1165  return constval.smallintval == NULL_SMALLINT;
1166  case kBIGINT:
1167  case kNUMERIC:
1168  case kDECIMAL:
1169  return constval.bigintval == NULL_BIGINT;
1170  case kTIME:
1171  case kTIMESTAMP:
1172  case kDATE:
1173  return constval.bigintval == NULL_BIGINT;
1174  case kVARCHAR:
1175  case kCHAR:
1176  case kTEXT:
1177  return constval.stringval == nullptr;
1178  case kPOINT:
1179  case kLINESTRING:
1180  case kPOLYGON:
1181  case kMULTIPOLYGON:
1182  return constval.stringval == nullptr;
1183  case kFLOAT:
1184  return constval.floatval == NULL_FLOAT;
1185  case kDOUBLE:
1186  return constval.doubleval == NULL_DOUBLE;
1187  case kNULLT:
1188  return constval.bigintval == 0;
1189  case kARRAY:
1190  return constval.arrayval == nullptr;
1191  default:
1192  UNREACHABLE();
1193  }
1194  UNREACHABLE();
1195  return false;
1196 }
1197 
1198 } // namespace
1199 
1200 void Constant::do_cast(const SQLTypeInfo& new_type_info) {
1201  if (type_info == new_type_info) {
1202  return;
1203  }
1204  if (is_null && !new_type_info.get_notnull()) {
1205  type_info = new_type_info;
1206  set_null_value();
1207  return;
1208  }
1209  if ((new_type_info.is_number() || new_type_info.get_type() == kTIMESTAMP) &&
1210  (new_type_info.get_type() != kTIMESTAMP || type_info.get_type() != kTIMESTAMP) &&
1212  type_info.get_type() == kBOOLEAN)) {
1213  cast_number(new_type_info);
1214  } else if (new_type_info.is_geometry() && type_info.is_string()) {
1215  type_info = new_type_info;
1216  } else if (new_type_info.is_geometry() &&
1217  type_info.get_type() == new_type_info.get_type()) {
1218  type_info = new_type_info;
1219  } else if (new_type_info.is_boolean() && type_info.is_boolean()) {
1220  type_info = new_type_info;
1221  } else if (new_type_info.is_string() && type_info.is_string()) {
1222  cast_string(new_type_info);
1223  } else if (type_info.is_string() || type_info.get_type() == kVARCHAR) {
1224  cast_from_string(new_type_info);
1225  } else if (new_type_info.is_string()) {
1226  cast_to_string(new_type_info);
1227  } else if (new_type_info.get_type() == kDATE && type_info.get_type() == kDATE) {
1228  type_info = new_type_info;
1229  } else if (new_type_info.get_type() == kDATE && type_info.get_type() == kTIMESTAMP) {
1236  type_info = new_type_info;
1237  } else if ((type_info.get_type() == kTIMESTAMP || type_info.get_type() == kDATE) &&
1238  new_type_info.get_type() == kTIMESTAMP) {
1239  const auto dimen = (type_info.get_type() == kDATE) ? 0 : type_info.get_dimension();
1240  if (dimen != new_type_info.get_dimension()) {
1241  constval.bigintval = dimen < new_type_info.get_dimension()
1245  new_type_info.get_dimension() - dimen)
1249  dimen - new_type_info.get_dimension());
1250  }
1251  type_info = new_type_info;
1252  } else if (new_type_info.is_array() && type_info.is_array()) {
1253  auto new_sub_ti = new_type_info.get_elem_type();
1254  for (auto& v : value_list) {
1255  auto c = std::dynamic_pointer_cast<Analyzer::Constant>(v);
1256  if (!c) {
1257  throw std::runtime_error("Invalid array cast.");
1258  }
1259  c->do_cast(new_sub_ti);
1260  }
1261  type_info = new_type_info;
1262  } else if (get_is_null() && (new_type_info.is_number() || new_type_info.is_time() ||
1263  new_type_info.is_string() || new_type_info.is_boolean())) {
1264  type_info = new_type_info;
1265  set_null_value();
1266  } else if (!is_null_value(type_info, constval) &&
1267  get_nullable_type_info(type_info) == new_type_info) {
1268  CHECK(!is_null);
1269  // relax nullability
1270  type_info = new_type_info;
1271  return;
1272  } else {
1273  throw std::runtime_error("Cast from " + type_info.get_type_name() + " to " +
1274  new_type_info.get_type_name() + " not supported");
1275  }
1276 }
1277 
1279  switch (type_info.get_type()) {
1280  case kBOOLEAN:
1282  break;
1283  case kTINYINT:
1285  break;
1286  case kINT:
1288  break;
1289  case kSMALLINT:
1291  break;
1292  case kBIGINT:
1293  case kNUMERIC:
1294  case kDECIMAL:
1296  break;
1297  case kTIME:
1298  case kTIMESTAMP:
1299  case kDATE:
1301  break;
1302  case kVARCHAR:
1303  case kCHAR:
1304  case kTEXT:
1305  constval.stringval = nullptr;
1306  break;
1307  case kPOINT:
1308  case kLINESTRING:
1309  case kPOLYGON:
1310  case kMULTIPOLYGON:
1311  constval.stringval = nullptr;
1312  break;
1313  case kFLOAT:
1315  break;
1316  case kDOUBLE:
1318  break;
1319  case kNULLT:
1320  constval.bigintval = 0;
1321  break;
1322  case kARRAY:
1323  constval.arrayval = nullptr;
1324  break;
1325  default:
1326  CHECK(false);
1327  }
1328 }
1329 
1330 std::shared_ptr<Analyzer::Expr> Constant::add_cast(const SQLTypeInfo& new_type_info) {
1331  if (is_null) {
1332  type_info = new_type_info;
1333  set_null_value();
1334  return shared_from_this();
1335  }
1336  if (new_type_info.get_compression() != type_info.get_compression()) {
1337  if (new_type_info.get_compression() != kENCODING_NONE) {
1338  SQLTypeInfo new_ti = new_type_info;
1339  if (new_ti.get_compression() != kENCODING_DATE_IN_DAYS) {
1341  }
1342  do_cast(new_ti);
1343  }
1344  return Expr::add_cast(new_type_info);
1345  }
1346  const auto is_integral_type =
1347  new_type_info.is_integer() || new_type_info.is_decimal() || new_type_info.is_fp();
1348  if (is_integral_type && (type_info.is_time() || type_info.is_date())) {
1349  // Let the codegen phase deal with casts from date/time to a number.
1350  return makeExpr<UOper>(new_type_info, contains_agg, kCAST, shared_from_this());
1351  }
1352  do_cast(new_type_info);
1353  return shared_from_this();
1354 }
1355 
1356 std::shared_ptr<Analyzer::Expr> UOper::add_cast(const SQLTypeInfo& new_type_info) {
1357  if (optype != kCAST) {
1358  return Expr::add_cast(new_type_info);
1359  }
1360  if (type_info.is_string() && new_type_info.is_string() &&
1361  new_type_info.get_compression() == kENCODING_DICT &&
1363  const SQLTypeInfo oti = operand->get_type_info();
1364  if (oti.is_string() && oti.get_compression() == kENCODING_DICT &&
1365  (oti.get_comp_param() == new_type_info.get_comp_param() ||
1366  oti.get_comp_param() == TRANSIENT_DICT(new_type_info.get_comp_param()))) {
1367  auto result = operand;
1368  operand = nullptr;
1369  return result;
1370  }
1371  }
1372  return Expr::add_cast(new_type_info);
1373 }
1374 
1375 std::shared_ptr<Analyzer::Expr> CaseExpr::add_cast(const SQLTypeInfo& new_type_info) {
1376  SQLTypeInfo ti = new_type_info;
1377  if (new_type_info.is_string() && new_type_info.get_compression() == kENCODING_DICT &&
1378  new_type_info.get_comp_param() == TRANSIENT_DICT_ID && type_info.is_string() &&
1382  }
1383 
1384  std::list<std::pair<std::shared_ptr<Analyzer::Expr>, std::shared_ptr<Analyzer::Expr>>>
1385  new_expr_pair_list;
1386  for (auto& p : expr_pair_list) {
1387  new_expr_pair_list.emplace_back(
1388  std::make_pair(p.first, p.second->deep_copy()->add_cast(ti)));
1389  }
1390 
1391  if (else_expr != nullptr) {
1392  else_expr = else_expr->add_cast(ti);
1393  }
1394  // Replace the current WHEN THEN pair list once we are sure all casts have succeeded
1395  expr_pair_list = new_expr_pair_list;
1396 
1397  type_info = ti;
1398  return shared_from_this();
1399 }
1400 
1401 std::shared_ptr<Analyzer::Expr> Subquery::add_cast(const SQLTypeInfo& new_type_info) {
1402  // not supported yet.
1403  CHECK(false);
1404  return nullptr;
1405 }
1406 
1407 int Query::get_rte_idx(const std::string& name) const {
1408  int rte_idx = 0;
1409  for (auto rte : rangetable) {
1410  if (rte->get_rangevar() == name) {
1411  return rte_idx;
1412  }
1413  rte_idx++;
1414  }
1415  return -1;
1416 }
1417 
1419  rangetable.push_back(rte);
1420 }
1421 
1423  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
1424  if (!groupby.empty()) {
1425  for (auto e : groupby) {
1426  auto c = std::dynamic_pointer_cast<ColumnVar>(e);
1427  if (c && table_id == c->get_table_id() && column_id == c->get_column_id()) {
1428  return;
1429  }
1430  }
1431  }
1432  throw std::runtime_error(
1433  "expressions in the SELECT or HAVING clause must be an aggregate function or an "
1434  "expression "
1435  "over GROUP BY columns.");
1436 }
1437 
1439  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
1440  if (which_row != kGROUPBY) {
1441  throw std::runtime_error("Internal error: invalid VAR in GROUP BY or HAVING.");
1442  }
1443 }
1444 
1446  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
1447  operand->check_group_by(groupby);
1448 }
1449 
1451  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
1452  left_operand->check_group_by(groupby);
1453  right_operand->check_group_by(groupby);
1454 }
1455 
1456 namespace {
1457 
1458 template <class T>
1459 bool expr_is(const std::shared_ptr<Analyzer::Expr>& expr) {
1460  return std::dynamic_pointer_cast<T>(expr) != nullptr;
1461 }
1462 
1463 } // namespace
1464 
1466  const std::shared_ptr<Analyzer::Expr> cast_operand,
1467  const std::shared_ptr<Analyzer::Expr> const_operand) {
1468  if (expr_is<UOper>(cast_operand) && expr_is<Constant>(const_operand)) {
1469  auto u_expr = std::dynamic_pointer_cast<UOper>(cast_operand);
1470  if (u_expr->get_optype() != kCAST) {
1471  return false;
1472  }
1473  if (!(expr_is<Analyzer::ColumnVar>(u_expr->get_own_operand()) &&
1474  !expr_is<Analyzer::Var>(u_expr->get_own_operand()))) {
1475  return false;
1476  }
1477  const auto& ti = u_expr->get_type_info();
1478  if (ti.is_time() && u_expr->get_operand()->get_type_info().is_time()) {
1479  // Allow casts between time types to pass through
1480  return true;
1481  } else if (ti.is_integer() && u_expr->get_operand()->get_type_info().is_integer()) {
1482  // Allow casts between integer types to pass through
1483  return true;
1484  }
1485  }
1486  return false;
1487 }
1488 
1489 std::shared_ptr<Analyzer::Expr> BinOper::normalize_simple_predicate(int& rte_idx) const {
1490  rte_idx = -1;
1491  if (!IS_COMPARISON(optype) || qualifier != kONE) {
1492  return nullptr;
1493  }
1494  if (expr_is<UOper>(left_operand)) {
1496  auto uo = std::dynamic_pointer_cast<UOper>(left_operand);
1497  auto cv = std::dynamic_pointer_cast<ColumnVar>(uo->get_own_operand());
1498  rte_idx = cv->get_rte_idx();
1499  return this->deep_copy();
1500  }
1501  } else if (expr_is<UOper>(right_operand)) {
1503  auto uo = std::dynamic_pointer_cast<UOper>(right_operand);
1504  auto cv = std::dynamic_pointer_cast<ColumnVar>(uo->get_own_operand());
1505  rte_idx = cv->get_rte_idx();
1506  return makeExpr<BinOper>(type_info,
1507  contains_agg,
1509  qualifier,
1510  right_operand->deep_copy(),
1511  left_operand->deep_copy());
1512  }
1513  } else if (expr_is<ColumnVar>(left_operand) && !expr_is<Var>(left_operand) &&
1514  expr_is<Constant>(right_operand)) {
1515  auto cv = std::dynamic_pointer_cast<ColumnVar>(left_operand);
1516  rte_idx = cv->get_rte_idx();
1517  return this->deep_copy();
1518  } else if (expr_is<Constant>(left_operand) && expr_is<ColumnVar>(right_operand) &&
1519  !expr_is<Var>(right_operand)) {
1520  auto cv = std::dynamic_pointer_cast<ColumnVar>(right_operand);
1521  rte_idx = cv->get_rte_idx();
1522  return makeExpr<BinOper>(type_info,
1523  contains_agg,
1525  qualifier,
1526  right_operand->deep_copy(),
1527  left_operand->deep_copy());
1528  }
1529  return nullptr;
1530 }
1531 
1532 void ColumnVar::group_predicates(std::list<const Expr*>& scan_predicates,
1533  std::list<const Expr*>& join_predicates,
1534  std::list<const Expr*>& const_predicates) const {
1535  if (type_info.get_type() == kBOOLEAN) {
1536  scan_predicates.push_back(this);
1537  }
1538 }
1539 
1540 void UOper::group_predicates(std::list<const Expr*>& scan_predicates,
1541  std::list<const Expr*>& join_predicates,
1542  std::list<const Expr*>& const_predicates) const {
1543  std::set<int> rte_idx_set;
1544  operand->collect_rte_idx(rte_idx_set);
1545  if (rte_idx_set.size() > 1) {
1546  join_predicates.push_back(this);
1547  } else if (rte_idx_set.size() == 1) {
1548  scan_predicates.push_back(this);
1549  } else {
1550  const_predicates.push_back(this);
1551  }
1552 }
1553 
1554 void BinOper::group_predicates(std::list<const Expr*>& scan_predicates,
1555  std::list<const Expr*>& join_predicates,
1556  std::list<const Expr*>& const_predicates) const {
1557  if (optype == kAND) {
1558  left_operand->group_predicates(scan_predicates, join_predicates, const_predicates);
1559  right_operand->group_predicates(scan_predicates, join_predicates, const_predicates);
1560  return;
1561  }
1562  std::set<int> rte_idx_set;
1563  left_operand->collect_rte_idx(rte_idx_set);
1564  right_operand->collect_rte_idx(rte_idx_set);
1565  if (rte_idx_set.size() > 1) {
1566  join_predicates.push_back(this);
1567  } else if (rte_idx_set.size() == 1) {
1568  scan_predicates.push_back(this);
1569  } else {
1570  const_predicates.push_back(this);
1571  }
1572 }
1573 
1574 namespace {
1575 
1577  const auto const_expr = dynamic_cast<const Analyzer::Constant*>(expr);
1578  if (const_expr) {
1579  return const_expr->get_is_null();
1580  }
1581  const auto& expr_ti = expr->get_type_info();
1582  return !expr_ti.get_notnull();
1583 }
1584 
1585 bool is_in_values_nullable(const std::shared_ptr<Analyzer::Expr>& a,
1586  const std::list<std::shared_ptr<Analyzer::Expr>>& l) {
1587  if (is_expr_nullable(a.get())) {
1588  return true;
1589  }
1590  for (const auto& v : l) {
1591  if (is_expr_nullable(v.get())) {
1592  return true;
1593  }
1594  }
1595  return false;
1596 }
1597 
1598 } // namespace
1599 
1600 InValues::InValues(std::shared_ptr<Analyzer::Expr> a,
1601  const std::list<std::shared_ptr<Analyzer::Expr>>& l)
1602  : Expr(kBOOLEAN, !is_in_values_nullable(a, l)), arg(a), value_list(l) {}
1603 
1604 void InValues::group_predicates(std::list<const Expr*>& scan_predicates,
1605  std::list<const Expr*>& join_predicates,
1606  std::list<const Expr*>& const_predicates) const {
1607  std::set<int> rte_idx_set;
1608  arg->collect_rte_idx(rte_idx_set);
1609  if (rte_idx_set.size() > 1) {
1610  join_predicates.push_back(this);
1611  } else if (rte_idx_set.size() == 1) {
1612  scan_predicates.push_back(this);
1613  } else {
1614  const_predicates.push_back(this);
1615  }
1616 }
1617 
1618 InIntegerSet::InIntegerSet(const std::shared_ptr<const Analyzer::Expr> a,
1619  const std::vector<int64_t>& l,
1620  const bool not_null)
1621  : Expr(kBOOLEAN, not_null), arg(a), value_list(l) {}
1622 
1623 void CharLengthExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1624  std::list<const Expr*>& join_predicates,
1625  std::list<const Expr*>& const_predicates) const {
1626  std::set<int> rte_idx_set;
1627  arg->collect_rte_idx(rte_idx_set);
1628  if (rte_idx_set.size() > 1) {
1629  join_predicates.push_back(this);
1630  } else if (rte_idx_set.size() == 1) {
1631  scan_predicates.push_back(this);
1632  } else {
1633  const_predicates.push_back(this);
1634  }
1635 }
1636 
1637 void KeyForStringExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1638  std::list<const Expr*>& join_predicates,
1639  std::list<const Expr*>& const_predicates) const {
1640  std::set<int> rte_idx_set;
1641  arg->collect_rte_idx(rte_idx_set);
1642  if (rte_idx_set.size() > 1) {
1643  join_predicates.push_back(this);
1644  } else if (rte_idx_set.size() == 1) {
1645  scan_predicates.push_back(this);
1646  } else {
1647  const_predicates.push_back(this);
1648  }
1649 }
1650 
1651 void SampleRatioExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1652  std::list<const Expr*>& join_predicates,
1653  std::list<const Expr*>& const_predicates) const {
1654  std::set<int> rte_idx_set;
1655  arg->collect_rte_idx(rte_idx_set);
1656  if (rte_idx_set.size() > 1) {
1657  join_predicates.push_back(this);
1658  } else if (rte_idx_set.size() == 1) {
1659  scan_predicates.push_back(this);
1660  } else {
1661  const_predicates.push_back(this);
1662  }
1663 }
1664 
1665 void StringOper::group_predicates(std::list<const Expr*>& scan_predicates,
1666  std::list<const Expr*>& join_predicates,
1667  std::list<const Expr*>& const_predicates) const {
1668  std::set<int> rte_idx_set;
1669  for (const auto& arg : args_) {
1670  arg->collect_rte_idx(rte_idx_set);
1671  }
1672  if (rte_idx_set.size() > 1) {
1673  join_predicates.push_back(this);
1674  } else if (rte_idx_set.size() == 1) {
1675  scan_predicates.push_back(this);
1676  } else {
1677  const_predicates.push_back(this);
1678  }
1679 }
1680 
1681 void CardinalityExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1682  std::list<const Expr*>& join_predicates,
1683  std::list<const Expr*>& const_predicates) const {
1684  std::set<int> rte_idx_set;
1685  arg->collect_rte_idx(rte_idx_set);
1686  if (rte_idx_set.size() > 1) {
1687  join_predicates.push_back(this);
1688  } else if (rte_idx_set.size() == 1) {
1689  scan_predicates.push_back(this);
1690  } else {
1691  const_predicates.push_back(this);
1692  }
1693 }
1694 
1695 void LikeExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1696  std::list<const Expr*>& join_predicates,
1697  std::list<const Expr*>& const_predicates) const {
1698  std::set<int> rte_idx_set;
1699  arg->collect_rte_idx(rte_idx_set);
1700  if (rte_idx_set.size() > 1) {
1701  join_predicates.push_back(this);
1702  } else if (rte_idx_set.size() == 1) {
1703  scan_predicates.push_back(this);
1704  } else {
1705  const_predicates.push_back(this);
1706  }
1707 }
1708 
1709 void RegexpExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1710  std::list<const Expr*>& join_predicates,
1711  std::list<const Expr*>& const_predicates) const {
1712  std::set<int> rte_idx_set;
1713  arg->collect_rte_idx(rte_idx_set);
1714  if (rte_idx_set.size() > 1) {
1715  join_predicates.push_back(this);
1716  } else if (rte_idx_set.size() == 1) {
1717  scan_predicates.push_back(this);
1718  } else {
1719  const_predicates.push_back(this);
1720  }
1721 }
1722 
1723 void WidthBucketExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1724  std::list<const Expr*>& join_predicates,
1725  std::list<const Expr*>& const_predicates) const {
1726  std::set<int> rte_idx_set;
1727  target_value_->collect_rte_idx(rte_idx_set);
1728  if (rte_idx_set.size() > 1) {
1729  join_predicates.push_back(this);
1730  } else if (rte_idx_set.size() == 1) {
1731  scan_predicates.push_back(this);
1732  } else {
1733  const_predicates.push_back(this);
1734  }
1735 }
1736 
1737 void LikelihoodExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1738  std::list<const Expr*>& join_predicates,
1739  std::list<const Expr*>& const_predicates) const {
1740  std::set<int> rte_idx_set;
1741  arg->collect_rte_idx(rte_idx_set);
1742  if (rte_idx_set.size() > 1) {
1743  join_predicates.push_back(this);
1744  } else if (rte_idx_set.size() == 1) {
1745  scan_predicates.push_back(this);
1746  } else {
1747  const_predicates.push_back(this);
1748  }
1749 }
1750 
1751 void AggExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1752  std::list<const Expr*>& join_predicates,
1753  std::list<const Expr*>& const_predicates) const {
1754  std::set<int> rte_idx_set;
1755  arg->collect_rte_idx(rte_idx_set);
1756  if (rte_idx_set.size() > 1) {
1757  join_predicates.push_back(this);
1758  } else if (rte_idx_set.size() == 1) {
1759  scan_predicates.push_back(this);
1760  } else {
1761  const_predicates.push_back(this);
1762  }
1763 }
1764 
1765 void CaseExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1766  std::list<const Expr*>& join_predicates,
1767  std::list<const Expr*>& const_predicates) const {
1768  std::set<int> rte_idx_set;
1769  for (auto p : expr_pair_list) {
1770  p.first->collect_rte_idx(rte_idx_set);
1771  p.second->collect_rte_idx(rte_idx_set);
1772  }
1773  if (else_expr != nullptr) {
1774  else_expr->collect_rte_idx(rte_idx_set);
1775  }
1776  if (rte_idx_set.size() > 1) {
1777  join_predicates.push_back(this);
1778  } else if (rte_idx_set.size() == 1) {
1779  scan_predicates.push_back(this);
1780  } else {
1781  const_predicates.push_back(this);
1782  }
1783 }
1784 
1785 void ExtractExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1786  std::list<const Expr*>& join_predicates,
1787  std::list<const Expr*>& const_predicates) const {
1788  std::set<int> rte_idx_set;
1789  from_expr_->collect_rte_idx(rte_idx_set);
1790  if (rte_idx_set.size() > 1) {
1791  join_predicates.push_back(this);
1792  } else if (rte_idx_set.size() == 1) {
1793  scan_predicates.push_back(this);
1794  } else {
1795  const_predicates.push_back(this);
1796  }
1797 }
1798 
1799 void DateaddExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1800  std::list<const Expr*>& join_predicates,
1801  std::list<const Expr*>& const_predicates) const {
1802  std::set<int> rte_idx_set;
1803  number_->collect_rte_idx(rte_idx_set);
1804  datetime_->collect_rte_idx(rte_idx_set);
1805  if (rte_idx_set.size() > 1) {
1806  join_predicates.push_back(this);
1807  } else if (rte_idx_set.size() == 1) {
1808  scan_predicates.push_back(this);
1809  } else {
1810  const_predicates.push_back(this);
1811  }
1812 }
1813 
1814 void DatediffExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1815  std::list<const Expr*>& join_predicates,
1816  std::list<const Expr*>& const_predicates) const {
1817  std::set<int> rte_idx_set;
1818  start_->collect_rte_idx(rte_idx_set);
1819  end_->collect_rte_idx(rte_idx_set);
1820  if (rte_idx_set.size() > 1) {
1821  join_predicates.push_back(this);
1822  } else if (rte_idx_set.size() == 1) {
1823  scan_predicates.push_back(this);
1824  } else {
1825  const_predicates.push_back(this);
1826  }
1827 }
1828 
1829 void DatetruncExpr::group_predicates(std::list<const Expr*>& scan_predicates,
1830  std::list<const Expr*>& join_predicates,
1831  std::list<const Expr*>& const_predicates) const {
1832  std::set<int> rte_idx_set;
1833  from_expr_->collect_rte_idx(rte_idx_set);
1834  if (rte_idx_set.size() > 1) {
1835  join_predicates.push_back(this);
1836  } else if (rte_idx_set.size() == 1) {
1837  scan_predicates.push_back(this);
1838  } else {
1839  const_predicates.push_back(this);
1840  }
1841 }
1842 
1843 std::shared_ptr<Analyzer::Expr> ColumnVar::rewrite_with_targetlist(
1844  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1845  for (auto tle : tlist) {
1846  const Expr* e = tle->get_expr();
1847  const ColumnVar* colvar = dynamic_cast<const ColumnVar*>(e);
1848  if (colvar != nullptr) {
1849  if (table_id == colvar->get_table_id() && column_id == colvar->get_column_id()) {
1850  return colvar->deep_copy();
1851  }
1852  }
1853  }
1854  throw std::runtime_error("Internal error: cannot find ColumnVar in targetlist.");
1855 }
1856 
1857 std::shared_ptr<Analyzer::Expr> ColumnVar::rewrite_with_child_targetlist(
1858  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1859  int varno = 1;
1860  for (auto tle : tlist) {
1861  const Expr* e = tle->get_expr();
1862  const ColumnVar* colvar = dynamic_cast<const ColumnVar*>(e);
1863  if (colvar == nullptr) {
1864  throw std::runtime_error(
1865  "Internal Error: targetlist in rewrite_with_child_targetlist is not all "
1866  "columns.");
1867  }
1868  if (table_id == colvar->get_table_id() && column_id == colvar->get_column_id()) {
1869  return makeExpr<Var>(colvar->get_type_info(),
1870  colvar->get_table_id(),
1871  colvar->get_column_id(),
1872  colvar->get_rte_idx(),
1874  varno);
1875  }
1876  varno++;
1877  }
1878  throw std::runtime_error("Internal error: cannot find ColumnVar in child targetlist.");
1879 }
1880 
1881 std::shared_ptr<Analyzer::Expr> ColumnVar::rewrite_agg_to_var(
1882  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1883  int varno = 1;
1884  for (auto tle : tlist) {
1885  const Expr* e = tle->get_expr();
1886  if (typeid(*e) != typeid(AggExpr)) {
1887  const ColumnVar* colvar = dynamic_cast<const ColumnVar*>(e);
1888  if (colvar == nullptr) {
1889  throw std::runtime_error(
1890  "Internal Error: targetlist in rewrite_agg_to_var is not all columns and "
1891  "aggregates.");
1892  }
1893  if (table_id == colvar->get_table_id() && column_id == colvar->get_column_id()) {
1894  return makeExpr<Var>(colvar->get_type_info(),
1895  colvar->get_table_id(),
1896  colvar->get_column_id(),
1897  colvar->get_rte_idx(),
1899  varno);
1900  }
1901  }
1902  varno++;
1903  }
1904  throw std::runtime_error(
1905  "Internal error: cannot find ColumnVar from having clause in targetlist.");
1906 }
1907 
1908 std::shared_ptr<Analyzer::Expr> Var::rewrite_agg_to_var(
1909  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1910  int varno = 1;
1911  for (auto tle : tlist) {
1912  const Expr* e = tle->get_expr();
1913  if (*e == *this) {
1914  return makeExpr<Var>(e->get_type_info(), Var::kINPUT_OUTER, varno);
1915  }
1916  varno++;
1917  }
1918  throw std::runtime_error(
1919  "Internal error: cannot find Var from having clause in targetlist.");
1920 }
1921 
1922 std::shared_ptr<Analyzer::Expr> StringOper::rewrite_with_targetlist(
1923  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1924  std::vector<std::shared_ptr<Analyzer::Expr>> rewritten_args;
1925  for (const auto& arg : args_) {
1926  rewritten_args.emplace_back(arg->rewrite_with_targetlist(tlist));
1927  }
1928  return makeExpr<StringOper>(kind_, rewritten_args);
1929 }
1930 
1931 std::shared_ptr<Analyzer::Expr> StringOper::rewrite_with_child_targetlist(
1932  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1933  std::vector<std::shared_ptr<Analyzer::Expr>> rewritten_args;
1934  for (const auto& arg : args_) {
1935  rewritten_args.emplace_back(arg->rewrite_with_child_targetlist(tlist));
1936  }
1937  return makeExpr<StringOper>(kind_, rewritten_args);
1938 }
1939 
1940 std::shared_ptr<Analyzer::Expr> StringOper::rewrite_agg_to_var(
1941  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1942  std::vector<std::shared_ptr<Analyzer::Expr>> rewritten_args;
1943  for (const auto& arg : args_) {
1944  rewritten_args.emplace_back(arg->rewrite_agg_to_var(tlist));
1945  }
1946  return makeExpr<StringOper>(kind_, rewritten_args);
1947 }
1948 
1949 std::shared_ptr<Analyzer::Expr> InValues::rewrite_with_targetlist(
1950  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1951  std::list<std::shared_ptr<Analyzer::Expr>> new_value_list;
1952  for (auto v : value_list) {
1953  new_value_list.push_back(v->deep_copy());
1954  }
1955  return makeExpr<InValues>(arg->rewrite_with_targetlist(tlist), new_value_list);
1956 }
1957 
1958 std::shared_ptr<Analyzer::Expr> InValues::rewrite_with_child_targetlist(
1959  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1960  std::list<std::shared_ptr<Analyzer::Expr>> new_value_list;
1961  for (auto v : value_list) {
1962  new_value_list.push_back(v->deep_copy());
1963  }
1964  return makeExpr<InValues>(arg->rewrite_with_child_targetlist(tlist), new_value_list);
1965 }
1966 
1967 std::shared_ptr<Analyzer::Expr> InValues::rewrite_agg_to_var(
1968  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1969  std::list<std::shared_ptr<Analyzer::Expr>> new_value_list;
1970  for (auto v : value_list) {
1971  new_value_list.push_back(v->rewrite_agg_to_var(tlist));
1972  }
1973  return makeExpr<InValues>(arg->rewrite_agg_to_var(tlist), new_value_list);
1974 }
1975 
1976 std::shared_ptr<Analyzer::Expr> AggExpr::rewrite_with_targetlist(
1977  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1978  for (auto tle : tlist) {
1979  const Expr* e = tle->get_expr();
1980  if (typeid(*e) == typeid(AggExpr)) {
1981  const AggExpr* agg = dynamic_cast<const AggExpr*>(e);
1982  if (*this == *agg) {
1983  return agg->deep_copy();
1984  }
1985  }
1986  }
1987  throw std::runtime_error("Internal error: cannot find AggExpr in targetlist.");
1988 }
1989 
1990 std::shared_ptr<Analyzer::Expr> AggExpr::rewrite_with_child_targetlist(
1991  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
1992  return makeExpr<AggExpr>(type_info,
1993  aggtype,
1994  arg ? arg->rewrite_with_child_targetlist(tlist) : nullptr,
1995  is_distinct,
1996  arg1);
1997 }
1998 
1999 std::shared_ptr<Analyzer::Expr> AggExpr::rewrite_agg_to_var(
2000  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2001  int varno = 1;
2002  for (auto tle : tlist) {
2003  const Expr* e = tle->get_expr();
2004  if (typeid(*e) == typeid(AggExpr)) {
2005  const AggExpr* agg_expr = dynamic_cast<const AggExpr*>(e);
2006  if (*this == *agg_expr) {
2007  return makeExpr<Var>(agg_expr->get_type_info(), Var::kINPUT_OUTER, varno);
2008  }
2009  }
2010  varno++;
2011  }
2012  throw std::runtime_error(
2013  "Internal error: cannot find AggExpr from having clause in targetlist.");
2014 }
2015 
2016 std::shared_ptr<Analyzer::Expr> CaseExpr::rewrite_with_targetlist(
2017  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2018  std::list<std::pair<std::shared_ptr<Analyzer::Expr>, std::shared_ptr<Analyzer::Expr>>>
2019  epair_list;
2020  for (auto p : expr_pair_list) {
2021  epair_list.emplace_back(p.first->rewrite_with_targetlist(tlist),
2022  p.second->rewrite_with_targetlist(tlist));
2023  }
2024  return makeExpr<CaseExpr>(
2025  type_info,
2026  contains_agg,
2027  epair_list,
2028  else_expr ? else_expr->rewrite_with_targetlist(tlist) : nullptr);
2029 }
2030 
2031 std::shared_ptr<Analyzer::Expr> ExtractExpr::rewrite_with_targetlist(
2032  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2033  return makeExpr<ExtractExpr>(
2034  type_info, contains_agg, field_, from_expr_->rewrite_with_targetlist(tlist));
2035 }
2036 
2037 std::shared_ptr<Analyzer::Expr> DateaddExpr::rewrite_with_targetlist(
2038  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2039  return makeExpr<DateaddExpr>(type_info,
2040  field_,
2041  number_->rewrite_with_targetlist(tlist),
2042  datetime_->rewrite_with_targetlist(tlist));
2043 }
2044 
2045 std::shared_ptr<Analyzer::Expr> DatediffExpr::rewrite_with_targetlist(
2046  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2047  return makeExpr<DatediffExpr>(type_info,
2048  field_,
2049  start_->rewrite_with_targetlist(tlist),
2050  end_->rewrite_with_targetlist(tlist));
2051 }
2052 
2053 std::shared_ptr<Analyzer::Expr> DatetruncExpr::rewrite_with_targetlist(
2054  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2055  return makeExpr<DatetruncExpr>(
2056  type_info, contains_agg, field_, from_expr_->rewrite_with_targetlist(tlist));
2057 }
2058 
2059 std::shared_ptr<Analyzer::Expr> CaseExpr::rewrite_with_child_targetlist(
2060  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2061  std::list<std::pair<std::shared_ptr<Analyzer::Expr>, std::shared_ptr<Analyzer::Expr>>>
2062  epair_list;
2063  for (auto p : expr_pair_list) {
2064  epair_list.emplace_back(p.first->rewrite_with_child_targetlist(tlist),
2065  p.second->rewrite_with_child_targetlist(tlist));
2066  }
2067  return makeExpr<CaseExpr>(
2068  type_info,
2069  contains_agg,
2070  epair_list,
2071  else_expr ? else_expr->rewrite_with_child_targetlist(tlist) : nullptr);
2072 }
2073 
2074 std::shared_ptr<Analyzer::Expr> ExtractExpr::rewrite_with_child_targetlist(
2075  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2076  return makeExpr<ExtractExpr>(
2077  type_info, contains_agg, field_, from_expr_->rewrite_with_child_targetlist(tlist));
2078 }
2079 
2080 std::shared_ptr<Analyzer::Expr> DateaddExpr::rewrite_with_child_targetlist(
2081  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2082  return makeExpr<DateaddExpr>(type_info,
2083  field_,
2084  number_->rewrite_with_child_targetlist(tlist),
2085  datetime_->rewrite_with_child_targetlist(tlist));
2086 }
2087 
2088 std::shared_ptr<Analyzer::Expr> DatediffExpr::rewrite_with_child_targetlist(
2089  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2090  return makeExpr<DatediffExpr>(type_info,
2091  field_,
2092  start_->rewrite_with_child_targetlist(tlist),
2093  end_->rewrite_with_child_targetlist(tlist));
2094 }
2095 
2096 std::shared_ptr<Analyzer::Expr> DatetruncExpr::rewrite_with_child_targetlist(
2097  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2098  return makeExpr<DatetruncExpr>(
2099  type_info, contains_agg, field_, from_expr_->rewrite_with_child_targetlist(tlist));
2100 }
2101 
2102 std::shared_ptr<Analyzer::Expr> CaseExpr::rewrite_agg_to_var(
2103  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2104  std::list<std::pair<std::shared_ptr<Analyzer::Expr>, std::shared_ptr<Analyzer::Expr>>>
2105  epair_list;
2106  for (auto p : expr_pair_list) {
2107  epair_list.emplace_back(p.first->rewrite_agg_to_var(tlist),
2108  p.second->rewrite_agg_to_var(tlist));
2109  }
2110  return makeExpr<CaseExpr>(type_info,
2111  contains_agg,
2112  epair_list,
2113  else_expr ? else_expr->rewrite_agg_to_var(tlist) : nullptr);
2114 }
2115 
2116 std::shared_ptr<Analyzer::Expr> ExtractExpr::rewrite_agg_to_var(
2117  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2118  return makeExpr<ExtractExpr>(
2119  type_info, contains_agg, field_, from_expr_->rewrite_agg_to_var(tlist));
2120 }
2121 
2122 std::shared_ptr<Analyzer::Expr> DateaddExpr::rewrite_agg_to_var(
2123  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2124  return makeExpr<DateaddExpr>(type_info,
2125  field_,
2126  number_->rewrite_agg_to_var(tlist),
2127  datetime_->rewrite_agg_to_var(tlist));
2128 }
2129 
2130 std::shared_ptr<Analyzer::Expr> DatediffExpr::rewrite_agg_to_var(
2131  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2132  return makeExpr<DatediffExpr>(type_info,
2133  field_,
2134  start_->rewrite_agg_to_var(tlist),
2135  end_->rewrite_agg_to_var(tlist));
2136 }
2137 
2138 std::shared_ptr<Analyzer::Expr> DatetruncExpr::rewrite_agg_to_var(
2139  const std::vector<std::shared_ptr<TargetEntry>>& tlist) const {
2140  return makeExpr<DatetruncExpr>(
2141  type_info, contains_agg, field_, from_expr_->rewrite_agg_to_var(tlist));
2142 }
2143 
2144 bool ColumnVar::operator==(const Expr& rhs) const {
2145  if (typeid(rhs) != typeid(ColumnVar) && typeid(rhs) != typeid(Var)) {
2146  return false;
2147  }
2148  const ColumnVar& rhs_cv = dynamic_cast<const ColumnVar&>(rhs);
2149  if (rte_idx != -1) {
2150  return (table_id == rhs_cv.get_table_id()) && (column_id == rhs_cv.get_column_id()) &&
2151  (rte_idx == rhs_cv.get_rte_idx());
2152  }
2153  const Var* v = dynamic_cast<const Var*>(this);
2154  if (v == nullptr) {
2155  return false;
2156  }
2157  const Var* rv = dynamic_cast<const Var*>(&rhs);
2158  if (rv == nullptr) {
2159  return false;
2160  }
2161  return (v->get_which_row() == rv->get_which_row()) &&
2162  (v->get_varno() == rv->get_varno());
2163 }
2164 
2165 bool ExpressionTuple::operator==(const Expr& rhs) const {
2166  const auto rhs_tuple = dynamic_cast<const ExpressionTuple*>(&rhs);
2167  if (!rhs_tuple) {
2168  return false;
2169  }
2170  const auto& rhs_tuple_cols = rhs_tuple->getTuple();
2171  return expr_list_match(tuple_, rhs_tuple_cols);
2172 }
2173 
2174 bool Datum_equal(const SQLTypeInfo& ti, Datum val1, Datum val2) {
2175  switch (ti.get_type()) {
2176  case kBOOLEAN:
2177  return val1.boolval == val2.boolval;
2178  case kCHAR:
2179  case kVARCHAR:
2180  case kTEXT:
2181  return *val1.stringval == *val2.stringval;
2182  case kNUMERIC:
2183  case kDECIMAL:
2184  case kBIGINT:
2185  return val1.bigintval == val2.bigintval;
2186  case kINT:
2187  return val1.intval == val2.intval;
2188  case kSMALLINT:
2189  return val1.smallintval == val2.smallintval;
2190  case kTINYINT:
2191  return val1.tinyintval == val2.tinyintval;
2192  case kFLOAT:
2193  return val1.floatval == val2.floatval;
2194  case kDOUBLE:
2195  return val1.doubleval == val2.doubleval;
2196  case kTIME:
2197  case kTIMESTAMP:
2198  case kDATE:
2199  case kINTERVAL_DAY_TIME:
2200  case kINTERVAL_YEAR_MONTH:
2201  return val1.bigintval == val2.bigintval;
2202  case kPOINT:
2203  case kLINESTRING:
2204  case kPOLYGON:
2205  case kMULTIPOLYGON:
2206  return *val1.stringval == *val2.stringval;
2207  default:
2208  throw std::runtime_error("Unrecognized type for Constant Datum equality: " +
2209  ti.get_type_name());
2210  }
2211  UNREACHABLE();
2212  return false;
2213 }
2214 
2215 bool Constant::operator==(const Expr& rhs) const {
2216  if (typeid(rhs) != typeid(Constant)) {
2217  return false;
2218  }
2219  const Constant& rhs_c = dynamic_cast<const Constant&>(rhs);
2220  if (type_info != rhs_c.get_type_info() || is_null != rhs_c.get_is_null()) {
2221  return false;
2222  }
2223  if (is_null && rhs_c.get_is_null()) {
2224  return true;
2225  }
2226  if (type_info.is_array()) {
2227  return false;
2228  }
2229  return Datum_equal(type_info, constval, rhs_c.get_constval());
2230 }
2231 
2232 bool UOper::operator==(const Expr& rhs) const {
2233  if (typeid(rhs) != typeid(UOper)) {
2234  return false;
2235  }
2236  const UOper& rhs_uo = dynamic_cast<const UOper&>(rhs);
2237  return optype == rhs_uo.get_optype() && *operand == *rhs_uo.get_operand();
2238 }
2239 
2240 bool BinOper::operator==(const Expr& rhs) const {
2241  if (typeid(rhs) != typeid(BinOper)) {
2242  return false;
2243  }
2244  const BinOper& rhs_bo = dynamic_cast<const BinOper&>(rhs);
2245  return optype == rhs_bo.get_optype() && *left_operand == *rhs_bo.get_left_operand() &&
2246  *right_operand == *rhs_bo.get_right_operand();
2247 }
2248 
2249 bool RangeOper::operator==(const Expr& rhs) const {
2250  if (typeid(rhs) != typeid(RangeOper)) {
2251  return false;
2252  }
2253  const RangeOper& rhs_rg = dynamic_cast<const RangeOper&>(rhs);
2254  return left_inclusive_ == rhs_rg.left_inclusive_ &&
2255  right_inclusive_ == rhs_rg.right_inclusive_ &&
2256  *left_operand_ == *rhs_rg.left_operand_ &&
2257  *right_operand_ == *rhs_rg.right_operand_;
2258 }
2259 
2260 bool CharLengthExpr::operator==(const Expr& rhs) const {
2261  if (typeid(rhs) != typeid(CharLengthExpr)) {
2262  return false;
2263  }
2264  const CharLengthExpr& rhs_cl = dynamic_cast<const CharLengthExpr&>(rhs);
2265  if (!(*arg == *rhs_cl.get_arg()) ||
2267  return false;
2268  }
2269  return true;
2270 }
2271 
2272 bool KeyForStringExpr::operator==(const Expr& rhs) const {
2273  if (typeid(rhs) != typeid(KeyForStringExpr)) {
2274  return false;
2275  }
2276  const KeyForStringExpr& rhs_cl = dynamic_cast<const KeyForStringExpr&>(rhs);
2277  if (!(*arg == *rhs_cl.get_arg())) {
2278  return false;
2279  }
2280  return true;
2281 }
2282 
2283 bool SampleRatioExpr::operator==(const Expr& rhs) const {
2284  if (typeid(rhs) != typeid(SampleRatioExpr)) {
2285  return false;
2286  }
2287  const SampleRatioExpr& rhs_cl = dynamic_cast<const SampleRatioExpr&>(rhs);
2288  if (!(*arg == *rhs_cl.get_arg())) {
2289  return false;
2290  }
2291  return true;
2292 }
2293 
2294 bool CardinalityExpr::operator==(const Expr& rhs) const {
2295  if (typeid(rhs) != typeid(CardinalityExpr)) {
2296  return false;
2297  }
2298  const CardinalityExpr& rhs_ca = dynamic_cast<const CardinalityExpr&>(rhs);
2299  if (!(*arg == *rhs_ca.get_arg())) {
2300  return false;
2301  }
2302  return true;
2303 }
2304 
2305 bool LikeExpr::operator==(const Expr& rhs) const {
2306  if (typeid(rhs) != typeid(LikeExpr)) {
2307  return false;
2308  }
2309  const LikeExpr& rhs_lk = dynamic_cast<const LikeExpr&>(rhs);
2310  if (!(*arg == *rhs_lk.get_arg()) || !(*like_expr == *rhs_lk.get_like_expr()) ||
2311  is_ilike != rhs_lk.get_is_ilike()) {
2312  return false;
2313  }
2314  if (escape_expr.get() == rhs_lk.get_escape_expr()) {
2315  return true;
2316  }
2317  if (escape_expr != nullptr && rhs_lk.get_escape_expr() != nullptr &&
2318  *escape_expr == *rhs_lk.get_escape_expr()) {
2319  return true;
2320  }
2321  return false;
2322 }
2323 
2324 bool RegexpExpr::operator==(const Expr& rhs) const {
2325  if (typeid(rhs) != typeid(RegexpExpr)) {
2326  return false;
2327  }
2328  const RegexpExpr& rhs_re = dynamic_cast<const RegexpExpr&>(rhs);
2329  if (!(*arg == *rhs_re.get_arg()) || !(*pattern_expr == *rhs_re.get_pattern_expr())) {
2330  return false;
2331  }
2332  if (escape_expr.get() == rhs_re.get_escape_expr()) {
2333  return true;
2334  }
2335  if (escape_expr != nullptr && rhs_re.get_escape_expr() != nullptr &&
2336  *escape_expr == *rhs_re.get_escape_expr()) {
2337  return true;
2338  }
2339  return false;
2340 }
2341 
2342 bool WidthBucketExpr::operator==(const Expr& rhs) const {
2343  if (typeid(rhs) != typeid(WidthBucketExpr)) {
2344  return false;
2345  }
2346  const WidthBucketExpr& rhs_l = dynamic_cast<const WidthBucketExpr&>(rhs);
2347  if (!(*target_value_ == *rhs_l.get_target_value())) {
2348  return false;
2349  }
2350  if (!(*lower_bound_ == *rhs_l.get_lower_bound())) {
2351  return false;
2352  }
2353  if (!(*upper_bound_ == *rhs_l.get_upper_bound())) {
2354  return false;
2355  }
2356  if (!(*partition_count_ == *rhs_l.get_partition_count())) {
2357  return false;
2358  }
2359  return true;
2360 }
2361 
2362 bool LikelihoodExpr::operator==(const Expr& rhs) const {
2363  if (typeid(rhs) != typeid(LikelihoodExpr)) {
2364  return false;
2365  }
2366  const LikelihoodExpr& rhs_l = dynamic_cast<const LikelihoodExpr&>(rhs);
2367  if (!(*arg == *rhs_l.get_arg())) {
2368  return false;
2369  }
2370  if (likelihood != rhs_l.get_likelihood()) {
2371  return false;
2372  }
2373  return true;
2374 }
2375 
2376 bool InValues::operator==(const Expr& rhs) const {
2377  if (typeid(rhs) != typeid(InValues)) {
2378  return false;
2379  }
2380  const InValues& rhs_iv = dynamic_cast<const InValues&>(rhs);
2381  if (!(*arg == *rhs_iv.get_arg())) {
2382  return false;
2383  }
2384  if (value_list.size() != rhs_iv.get_value_list().size()) {
2385  return false;
2386  }
2387  auto q = rhs_iv.get_value_list().begin();
2388  for (auto p : value_list) {
2389  if (!(*p == **q)) {
2390  return false;
2391  }
2392  q++;
2393  }
2394  return true;
2395 }
2396 
2397 bool AggExpr::operator==(const Expr& rhs) const {
2398  if (typeid(rhs) != typeid(AggExpr)) {
2399  return false;
2400  }
2401  const AggExpr& rhs_ae = dynamic_cast<const AggExpr&>(rhs);
2402  if (aggtype != rhs_ae.get_aggtype() || is_distinct != rhs_ae.get_is_distinct()) {
2403  return false;
2404  }
2405  if (arg.get() == rhs_ae.get_arg()) {
2406  return true;
2407  }
2408  if (arg == nullptr || rhs_ae.get_arg() == nullptr) {
2409  return false;
2410  }
2411  return *arg == *rhs_ae.get_arg();
2412 }
2413 
2414 bool CaseExpr::operator==(const Expr& rhs) const {
2415  if (typeid(rhs) != typeid(CaseExpr)) {
2416  return false;
2417  }
2418  const CaseExpr& rhs_ce = dynamic_cast<const CaseExpr&>(rhs);
2419  if (expr_pair_list.size() != rhs_ce.get_expr_pair_list().size()) {
2420  return false;
2421  }
2422  if ((else_expr == nullptr && rhs_ce.get_else_expr() != nullptr) ||
2423  (else_expr != nullptr && rhs_ce.get_else_expr() == nullptr)) {
2424  return false;
2425  }
2426  auto it = rhs_ce.get_expr_pair_list().cbegin();
2427  for (auto p : expr_pair_list) {
2428  if (!(*p.first == *it->first) || !(*p.second == *it->second)) {
2429  return false;
2430  }
2431  ++it;
2432  }
2433  return else_expr == nullptr ||
2434  (else_expr != nullptr && *else_expr == *rhs_ce.get_else_expr());
2435 }
2436 
2437 bool ExtractExpr::operator==(const Expr& rhs) const {
2438  if (typeid(rhs) != typeid(ExtractExpr)) {
2439  return false;
2440  }
2441  const ExtractExpr& rhs_ee = dynamic_cast<const ExtractExpr&>(rhs);
2442  return field_ == rhs_ee.get_field() && *from_expr_ == *rhs_ee.get_from_expr();
2443 }
2444 
2445 bool DateaddExpr::operator==(const Expr& rhs) const {
2446  if (typeid(rhs) != typeid(DateaddExpr)) {
2447  return false;
2448  }
2449  const DateaddExpr& rhs_ee = dynamic_cast<const DateaddExpr&>(rhs);
2450  return field_ == rhs_ee.get_field() && *number_ == *rhs_ee.get_number_expr() &&
2451  *datetime_ == *rhs_ee.get_datetime_expr();
2452 }
2453 
2454 bool DatediffExpr::operator==(const Expr& rhs) const {
2455  if (typeid(rhs) != typeid(DatediffExpr)) {
2456  return false;
2457  }
2458  const DatediffExpr& rhs_ee = dynamic_cast<const DatediffExpr&>(rhs);
2459  return field_ == rhs_ee.get_field() && *start_ == *rhs_ee.get_start_expr() &&
2460  *end_ == *rhs_ee.get_end_expr();
2461 }
2462 
2463 bool DatetruncExpr::operator==(const Expr& rhs) const {
2464  if (typeid(rhs) != typeid(DatetruncExpr)) {
2465  return false;
2466  }
2467  const DatetruncExpr& rhs_ee = dynamic_cast<const DatetruncExpr&>(rhs);
2468  return field_ == rhs_ee.get_field() && *from_expr_ == *rhs_ee.get_from_expr();
2469 }
2470 
2471 bool OffsetInFragment::operator==(const Expr& rhs) const {
2472  return typeid(rhs) == typeid(OffsetInFragment);
2473 }
2474 
2475 bool WindowFunction::operator==(const Expr& rhs) const {
2476  const auto rhs_window = dynamic_cast<const WindowFunction*>(&rhs);
2477  if (!rhs_window) {
2478  return false;
2479  }
2480  if (kind_ != rhs_window->kind_ || args_.size() != rhs_window->args_.size() ||
2481  partition_keys_.size() != rhs_window->partition_keys_.size() ||
2482  order_keys_.size() != rhs_window->order_keys_.size()) {
2483  return false;
2484  }
2485  return expr_list_match(args_, rhs_window->args_) &&
2486  expr_list_match(partition_keys_, rhs_window->partition_keys_) &&
2487  expr_list_match(order_keys_, rhs_window->order_keys_);
2488 }
2489 
2490 bool ArrayExpr::operator==(Expr const& rhs) const {
2491  if (typeid(rhs) != typeid(ArrayExpr)) {
2492  return false;
2493  }
2494  ArrayExpr const& casted_rhs = static_cast<ArrayExpr const&>(rhs);
2495  for (unsigned i = 0; i < contained_expressions_.size(); i++) {
2496  auto& lhs_expr = contained_expressions_[i];
2497  auto& rhs_expr = casted_rhs.contained_expressions_[i];
2498  if (!(lhs_expr == rhs_expr)) {
2499  return false;
2500  }
2501  }
2502  if (isNull() != casted_rhs.isNull()) {
2503  return false;
2504  }
2505 
2506  return true;
2507  ;
2508 }
2509 
2510 bool GeoUOper::operator==(const Expr& rhs) const {
2511  const auto rhs_geo = dynamic_cast<const GeoUOper*>(&rhs);
2512  if (!rhs_geo) {
2513  return false;
2514  }
2515  if (op_ != rhs_geo->getOp() || ti0_ != rhs_geo->getTypeInfo0() ||
2516  args0_.size() != rhs_geo->getArgs0().size()) {
2517  return false;
2518  }
2519  return expr_list_match(args0_, rhs_geo->getArgs0());
2520 }
2521 
2522 bool GeoBinOper::operator==(const Expr& rhs) const {
2523  const auto rhs_geo = dynamic_cast<const GeoBinOper*>(&rhs);
2524  if (!rhs_geo) {
2525  return false;
2526  }
2527  if (op_ != rhs_geo->getOp() || ti0_ != rhs_geo->getTypeInfo0() ||
2528  args0_.size() != rhs_geo->getArgs0().size()) {
2529  return false;
2530  }
2531  if (ti1_ != rhs_geo->getTypeInfo1() || args1_.size() != rhs_geo->getArgs1().size()) {
2532  return false;
2533  }
2534  return expr_list_match(args0_, rhs_geo->getArgs0()) ||
2535  expr_list_match(args1_, rhs_geo->getArgs1());
2536 }
2537 
2538 std::string ColumnVar::toString() const {
2539  return "(ColumnVar table: " + std::to_string(table_id) +
2540  " column: " + std::to_string(column_id) + " rte: " + std::to_string(rte_idx) +
2541  " " + get_type_info().get_type_name() + ") ";
2542 }
2543 
2544 std::string ExpressionTuple::toString() const {
2545  std::string str{"< "};
2546  for (const auto& column : tuple_) {
2547  str += column->toString();
2548  }
2549  str += "> ";
2550  return str;
2551 }
2552 
2553 std::string Var::toString() const {
2554  return "(Var table: " + std::to_string(table_id) +
2555  " column: " + std::to_string(column_id) + " rte: " + std::to_string(rte_idx) +
2556  " which_row: " + std::to_string(which_row) + " varno: " + std::to_string(varno) +
2557  ") ";
2558 }
2559 
2560 std::string Constant::toString() const {
2561  std::string str{"(Const "};
2562  if (is_null) {
2563  str += "NULL";
2564  } else if (type_info.is_array()) {
2565  const auto& elem_ti = type_info.get_elem_type();
2566  str += ::toString(type_info.get_type()) + ": " + ::toString(elem_ti.get_type());
2567  } else {
2568  str += DatumToString(constval, type_info);
2569  }
2570  str += ") ";
2571  return str;
2572 }
2573 
2574 std::string UOper::toString() const {
2575  std::string op;
2576  switch (optype) {
2577  case kNOT:
2578  op = "NOT ";
2579  break;
2580  case kUMINUS:
2581  op = "- ";
2582  break;
2583  case kISNULL:
2584  op = "IS NULL ";
2585  break;
2586  case kEXISTS:
2587  op = "EXISTS ";
2588  break;
2589  case kCAST:
2590  op = "CAST " + type_info.get_type_name() + "(" +
2592  std::to_string(type_info.get_scale()) + ") " +
2595  break;
2596  case kUNNEST:
2597  op = "UNNEST ";
2598  break;
2599  default:
2600  break;
2601  }
2602  return "(" + op + operand->toString() + ") ";
2603 }
2604 
2605 std::string BinOper::toString() const {
2606  std::string op;
2607  switch (optype) {
2608  case kEQ:
2609  op = "= ";
2610  break;
2611  case kNE:
2612  op = "<> ";
2613  break;
2614  case kLT:
2615  op = "< ";
2616  break;
2617  case kLE:
2618  op = "<= ";
2619  break;
2620  case kGT:
2621  op = "> ";
2622  break;
2623  case kGE:
2624  op = ">= ";
2625  break;
2626  case kAND:
2627  op = "AND ";
2628  break;
2629  case kOR:
2630  op = "OR ";
2631  break;
2632  case kMINUS:
2633  op = "- ";
2634  break;
2635  case kPLUS:
2636  op = "+ ";
2637  break;
2638  case kMULTIPLY:
2639  op = "* ";
2640  break;
2641  case kDIVIDE:
2642  op = "/ ";
2643  break;
2644  case kMODULO:
2645  op = "% ";
2646  break;
2647  case kARRAY_AT:
2648  op = "[] ";
2649  break;
2650  case kOVERLAPS:
2651  op = "OVERLAPS ";
2652  break;
2653  default:
2654  break;
2655  }
2656  std::string str{"("};
2657  str += op;
2658  if (qualifier == kANY) {
2659  str += "ANY ";
2660  } else if (qualifier == kALL) {
2661  str += "ALL ";
2662  }
2663  str += left_operand->toString();
2664  str += right_operand->toString();
2665  str += ") ";
2666  return str;
2667 }
2668 
2669 std::string RangeOper::toString() const {
2670  const std::string lhs = left_inclusive_ ? "[" : "(";
2671  const std::string rhs = right_inclusive_ ? "]" : ")";
2672  return "(RangeOper " + lhs + " " + left_operand_->toString() + " , " +
2673  right_operand_->toString() + " " + rhs + " )";
2674 }
2675 
2676 std::string Subquery::toString() const {
2677  return "(Subquery ) ";
2678 }
2679 
2680 std::string InValues::toString() const {
2681  std::string str{"(IN "};
2682  str += arg->toString();
2683  str += "(";
2684  int cnt = 0;
2685  bool shorted_value_list_str = false;
2686  for (auto e : value_list) {
2687  str += e->toString();
2688  cnt++;
2689  if (cnt > 4) {
2690  shorted_value_list_str = true;
2691  break;
2692  }
2693  }
2694  if (shorted_value_list_str) {
2695  str += "... | ";
2696  str += "Total # values: ";
2697  str += std::to_string(value_list.size());
2698  }
2699  str += ") ";
2700  return str;
2701 }
2702 
2703 std::shared_ptr<Analyzer::Expr> InIntegerSet::deep_copy() const {
2704  return std::make_shared<InIntegerSet>(arg, value_list, get_type_info().get_notnull());
2705 }
2706 
2707 bool InIntegerSet::operator==(const Expr& rhs) const {
2708  if (!dynamic_cast<const InIntegerSet*>(&rhs)) {
2709  return false;
2710  }
2711  const auto& rhs_in_integer_set = static_cast<const InIntegerSet&>(rhs);
2712  return *arg == *rhs_in_integer_set.arg && value_list == rhs_in_integer_set.value_list;
2713 }
2714 
2715 std::string InIntegerSet::toString() const {
2716  std::string str{"(IN_INTEGER_SET "};
2717  str += arg->toString();
2718  str += "( ";
2719  int cnt = 0;
2720  bool shorted_value_list_str = false;
2721  for (const auto e : value_list) {
2722  str += std::to_string(e) + " ";
2723  cnt++;
2724  if (cnt > 4) {
2725  shorted_value_list_str = true;
2726  break;
2727  }
2728  }
2729  if (shorted_value_list_str) {
2730  str += "... | ";
2731  str += "Total # values: ";
2732  str += std::to_string(value_list.size());
2733  }
2734  str += ") ";
2735  return str;
2736 }
2737 
2738 std::string CharLengthExpr::toString() const {
2739  std::string str;
2740  if (calc_encoded_length) {
2741  str += "CHAR_LENGTH(";
2742  } else {
2743  str += "LENGTH(";
2744  }
2745  str += arg->toString();
2746  str += ") ";
2747  return str;
2748 }
2749 
2750 std::string KeyForStringExpr::toString() const {
2751  std::string str{"KEY_FOR_STRING("};
2752  str += arg->toString();
2753  str += ") ";
2754  return str;
2755 }
2756 
2757 std::string SampleRatioExpr::toString() const {
2758  std::string str{"SAMPLE_RATIO("};
2759  str += arg->toString();
2760  str += ") ";
2761  return str;
2762 }
2763 
2764 std::string CardinalityExpr::toString() const {
2765  std::string str{"CARDINALITY("};
2766  str += arg->toString();
2767  str += ") ";
2768  return str;
2769 }
2770 
2771 std::string LikeExpr::toString() const {
2772  std::string str{"(LIKE "};
2773  str += arg->toString();
2774  str += like_expr->toString();
2775  if (escape_expr) {
2776  str += escape_expr->toString();
2777  }
2778  str += ") ";
2779  return str;
2780 }
2781 
2782 std::string RegexpExpr::toString() const {
2783  std::string str{"(REGEXP "};
2784  str += arg->toString();
2785  str += pattern_expr->toString();
2786  if (escape_expr) {
2787  str += escape_expr->toString();
2788  }
2789  str += ") ";
2790  return str;
2791 }
2792 
2793 std::string WidthBucketExpr::toString() const {
2794  std::string str{"(WIDTH_BUCKET "};
2795  str += target_value_->toString();
2796  str += lower_bound_->toString();
2797  str += upper_bound_->toString();
2798  str += partition_count_->toString();
2799  return str + ") ";
2800 }
2801 
2802 std::string LikelihoodExpr::toString() const {
2803  std::string str{"(LIKELIHOOD "};
2804  str += arg->toString();
2805  return str + " " + std::to_string(likelihood) + ") ";
2806 }
2807 
2808 std::string AggExpr::toString() const {
2809  std::string agg;
2810  switch (aggtype) {
2811  case kAVG:
2812  agg = "AVG ";
2813  break;
2814  case kMIN:
2815  agg = "MIN ";
2816  break;
2817  case kMAX:
2818  agg = "MAX ";
2819  break;
2820  case kSUM:
2821  agg = "SUM ";
2822  break;
2823  case kCOUNT:
2824  agg = "COUNT ";
2825  break;
2827  agg = "APPROX_COUNT_DISTINCT";
2828  break;
2829  case kAPPROX_QUANTILE:
2830  agg = "APPROX_PERCENTILE";
2831  break;
2832  case kSINGLE_VALUE:
2833  agg = "SINGLE_VALUE";
2834  break;
2835  case kSAMPLE:
2836  agg = "SAMPLE";
2837  break;
2838  }
2839  std::string str{"(" + agg};
2840  if (is_distinct) {
2841  str += "DISTINCT ";
2842  }
2843  if (arg) {
2844  str += arg->toString();
2845  } else {
2846  str += "*";
2847  }
2848  return str + ") ";
2849 }
2850 
2851 std::string CaseExpr::toString() const {
2852  std::string str{"CASE "};
2853  for (auto p : expr_pair_list) {
2854  str += "(";
2855  str += p.first->toString();
2856  str += ", ";
2857  str += p.second->toString();
2858  str += ") ";
2859  }
2860  if (else_expr) {
2861  str += "ELSE ";
2862  str += else_expr->toString();
2863  }
2864  str += " END ";
2865  return str;
2866 }
2867 
2868 std::string ExtractExpr::toString() const {
2869  return "EXTRACT(" + std::to_string(field_) + " FROM " + from_expr_->toString() + ") ";
2870 }
2871 
2872 std::string DateaddExpr::toString() const {
2873  return "DATEADD(" + std::to_string(field_) + " NUMBER " + number_->toString() +
2874  " DATETIME " + datetime_->toString() + ") ";
2875 }
2876 
2877 std::string DatediffExpr::toString() const {
2878  return "DATEDIFF(" + std::to_string(field_) + " START " + start_->toString() + " END " +
2879  end_->toString() + ") ";
2880 }
2881 
2882 std::string DatetruncExpr::toString() const {
2883  return "DATE_TRUNC(" + std::to_string(field_) + " , " + from_expr_->toString() + ") ";
2884 }
2885 
2886 std::string OffsetInFragment::toString() const {
2887  return "(OffsetInFragment) ";
2888 }
2889 
2890 std::string WindowFunction::toString() const {
2891  std::string result = "WindowFunction(" + ::toString(kind_);
2892  for (const auto& arg : args_) {
2893  result += " " + arg->toString();
2894  }
2895  return result + ") ";
2896 }
2897 
2898 std::string ArrayExpr::toString() const {
2899  std::string str{"ARRAY["};
2900 
2901  auto iter(contained_expressions_.begin());
2902  while (iter != contained_expressions_.end()) {
2903  str += (*iter)->toString();
2904  if (iter + 1 != contained_expressions_.end()) {
2905  str += ", ";
2906  }
2907  iter++;
2908  }
2909  str += "]";
2910  return str;
2911 }
2912 
2913 std::string GeoUOper::toString() const {
2914  std::string fn;
2915  switch (op_) {
2917  fn = "Geo";
2918  break;
2920  fn = "ST_IsEmpty";
2921  break;
2923  fn = "ST_IsValid";
2924  break;
2925  default:
2926  fn = "Geo_UNKNOWN";
2927  break;
2928  }
2929  std::string result = fn + "(";
2930  for (const auto& arg : args0_) {
2931  result += " " + arg->toString();
2932  }
2933  return result + " ) ";
2934 }
2935 
2936 std::string GeoBinOper::toString() const {
2937  std::string fn;
2938  switch (op_) {
2940  fn = "ST_Intersection";
2941  break;
2943  fn = "ST_Difference";
2944  break;
2946  fn = "ST_Union";
2947  break;
2949  fn = "ST_Buffer";
2950  break;
2951  default:
2952  fn = "Geo_UNKNOWN";
2953  break;
2954  }
2955  std::string result = fn + "(";
2956  // TODO: generate wkt
2957  for (const auto& arg : args0_) {
2958  result += " " + arg->toString();
2959  }
2960  for (const auto& arg : args1_) {
2961  result += " " + arg->toString();
2962  }
2963  return result + " ) ";
2964 }
2965 
2966 std::string TargetEntry::toString() const {
2967  std::string str{"(" + resname + " "};
2968  str += expr->toString();
2969  if (unnest) {
2970  str += " UNNEST";
2971  }
2972  str += ") ";
2973  return str;
2974 }
2975 
2976 std::string OrderEntry::toString() const {
2977  std::string str{std::to_string(tle_no)};
2978  if (is_desc) {
2979  str += " desc";
2980  }
2981  if (nulls_first) {
2982  str += " nulls first";
2983  }
2984  str += " ";
2985  return str;
2986 }
2987 
2988 void Expr::add_unique(std::list<const Expr*>& expr_list) const {
2989  // only add unique instances to the list
2990  for (auto e : expr_list) {
2991  if (*e == *this) {
2992  return;
2993  }
2994  }
2995  expr_list.push_back(this);
2996 }
2997 
2998 void BinOper::find_expr(bool (*f)(const Expr*), std::list<const Expr*>& expr_list) const {
2999  if (f(this)) {
3000  add_unique(expr_list);
3001  return;
3002  }
3003  left_operand->find_expr(f, expr_list);
3004  right_operand->find_expr(f, expr_list);
3005 }
3006 
3007 void UOper::find_expr(bool (*f)(const Expr*), std::list<const Expr*>& expr_list) const {
3008  if (f(this)) {
3009  add_unique(expr_list);
3010  return;
3011  }
3012  operand->find_expr(f, expr_list);
3013 }
3014 
3015 void InValues::find_expr(bool (*f)(const Expr*),
3016  std::list<const Expr*>& expr_list) const {
3017  if (f(this)) {
3018  add_unique(expr_list);
3019  return;
3020  }
3021  arg->find_expr(f, expr_list);
3022  for (auto e : value_list) {
3023  e->find_expr(f, expr_list);
3024  }
3025 }
3026 
3027 void CharLengthExpr::find_expr(bool (*f)(const Expr*),
3028  std::list<const Expr*>& expr_list) const {
3029  if (f(this)) {
3030  add_unique(expr_list);
3031  return;
3032  }
3033  arg->find_expr(f, expr_list);
3034 }
3035 
3036 void KeyForStringExpr::find_expr(bool (*f)(const Expr*),
3037  std::list<const Expr*>& expr_list) const {
3038  if (f(this)) {
3039  add_unique(expr_list);
3040  return;
3041  }
3042  arg->find_expr(f, expr_list);
3043 }
3044 
3045 void SampleRatioExpr::find_expr(bool (*f)(const Expr*),
3046  std::list<const Expr*>& expr_list) const {
3047  if (f(this)) {
3048  add_unique(expr_list);
3049  return;
3050  }
3051  arg->find_expr(f, expr_list);
3052 }
3053 
3054 void StringOper::find_expr(bool (*f)(const Expr*),
3055  std::list<const Expr*>& expr_list) const {
3056  if (f(this)) {
3057  add_unique(expr_list);
3058  return;
3059  }
3060  for (const auto& arg : args_) {
3061  arg->find_expr(f, expr_list);
3062  }
3063 }
3064 
3065 void CardinalityExpr::find_expr(bool (*f)(const Expr*),
3066  std::list<const Expr*>& expr_list) const {
3067  if (f(this)) {
3068  add_unique(expr_list);
3069  return;
3070  }
3071  arg->find_expr(f, expr_list);
3072 }
3073 
3074 void LikeExpr::find_expr(bool (*f)(const Expr*),
3075  std::list<const Expr*>& expr_list) const {
3076  if (f(this)) {
3077  add_unique(expr_list);
3078  return;
3079  }
3080  arg->find_expr(f, expr_list);
3081  like_expr->find_expr(f, expr_list);
3082  if (escape_expr != nullptr) {
3083  escape_expr->find_expr(f, expr_list);
3084  }
3085 }
3086 
3087 void RegexpExpr::find_expr(bool (*f)(const Expr*),
3088  std::list<const Expr*>& expr_list) const {
3089  if (f(this)) {
3090  add_unique(expr_list);
3091  return;
3092  }
3093  arg->find_expr(f, expr_list);
3094  pattern_expr->find_expr(f, expr_list);
3095  if (escape_expr != nullptr) {
3096  escape_expr->find_expr(f, expr_list);
3097  }
3098 }
3099 
3100 void WidthBucketExpr::find_expr(bool (*f)(const Expr*),
3101  std::list<const Expr*>& expr_list) const {
3102  if (f(this)) {
3103  add_unique(expr_list);
3104  return;
3105  }
3106  target_value_->find_expr(f, expr_list);
3107  lower_bound_->find_expr(f, expr_list);
3108  upper_bound_->find_expr(f, expr_list);
3109  partition_count_->find_expr(f, expr_list);
3110 }
3111 
3112 void LikelihoodExpr::find_expr(bool (*f)(const Expr*),
3113  std::list<const Expr*>& expr_list) const {
3114  if (f(this)) {
3115  add_unique(expr_list);
3116  return;
3117  }
3118  arg->find_expr(f, expr_list);
3119 }
3120 
3121 void AggExpr::find_expr(bool (*f)(const Expr*), std::list<const Expr*>& expr_list) const {
3122  if (f(this)) {
3123  add_unique(expr_list);
3124  return;
3125  }
3126  if (arg != nullptr) {
3127  arg->find_expr(f, expr_list);
3128  }
3129 }
3130 
3131 void CaseExpr::find_expr(bool (*f)(const Expr*),
3132  std::list<const Expr*>& expr_list) const {
3133  if (f(this)) {
3134  add_unique(expr_list);
3135  return;
3136  }
3137  for (auto p : expr_pair_list) {
3138  p.first->find_expr(f, expr_list);
3139  p.second->find_expr(f, expr_list);
3140  }
3141  if (else_expr != nullptr) {
3142  else_expr->find_expr(f, expr_list);
3143  }
3144 }
3145 
3146 void ExtractExpr::find_expr(bool (*f)(const Expr*),
3147  std::list<const Expr*>& expr_list) const {
3148  if (f(this)) {
3149  add_unique(expr_list);
3150  return;
3151  }
3152  from_expr_->find_expr(f, expr_list);
3153 }
3154 
3155 void DateaddExpr::find_expr(bool (*f)(const Expr*),
3156  std::list<const Expr*>& expr_list) const {
3157  if (f(this)) {
3158  add_unique(expr_list);
3159  return;
3160  }
3161  number_->find_expr(f, expr_list);
3162  datetime_->find_expr(f, expr_list);
3163 }
3164 
3165 void DatediffExpr::find_expr(bool (*f)(const Expr*),
3166  std::list<const Expr*>& expr_list) const {
3167  if (f(this)) {
3168  add_unique(expr_list);
3169  return;
3170  }
3171  start_->find_expr(f, expr_list);
3172  end_->find_expr(f, expr_list);
3173 }
3174 
3175 void DatetruncExpr::find_expr(bool (*f)(const Expr*),
3176  std::list<const Expr*>& expr_list) const {
3177  if (f(this)) {
3178  add_unique(expr_list);
3179  return;
3180  }
3181  from_expr_->find_expr(f, expr_list);
3182 }
3183 
3184 void CaseExpr::collect_rte_idx(std::set<int>& rte_idx_set) const {
3185  for (auto p : expr_pair_list) {
3186  p.first->collect_rte_idx(rte_idx_set);
3187  p.second->collect_rte_idx(rte_idx_set);
3188  }
3189  if (else_expr != nullptr) {
3190  else_expr->collect_rte_idx(rte_idx_set);
3191  }
3192 }
3193 
3194 void ExtractExpr::collect_rte_idx(std::set<int>& rte_idx_set) const {
3195  from_expr_->collect_rte_idx(rte_idx_set);
3196 }
3197 
3198 void DateaddExpr::collect_rte_idx(std::set<int>& rte_idx_set) const {
3199  number_->collect_rte_idx(rte_idx_set);
3200  datetime_->collect_rte_idx(rte_idx_set);
3201 }
3202 
3203 void DatediffExpr::collect_rte_idx(std::set<int>& rte_idx_set) const {
3204  start_->collect_rte_idx(rte_idx_set);
3205  end_->collect_rte_idx(rte_idx_set);
3206 }
3207 
3208 void DatetruncExpr::collect_rte_idx(std::set<int>& rte_idx_set) const {
3209  from_expr_->collect_rte_idx(rte_idx_set);
3210 }
3211 
3212 void ArrayExpr::collect_rte_idx(std::set<int>& rte_idx_set) const {
3213  for (unsigned i = 0; i < getElementCount(); i++) {
3214  const auto expr = getElement(i);
3215  expr->collect_rte_idx(rte_idx_set);
3216  }
3217 }
3218 
3219 void StringOper::collect_rte_idx(std::set<int>& rte_idx_set) const {
3220  for (const auto& arg : args_) {
3221  arg->collect_rte_idx(rte_idx_set);
3222  }
3223 }
3224 
3225 void FunctionOper::collect_rte_idx(std::set<int>& rte_idx_set) const {
3226  for (unsigned i = 0; i < getArity(); i++) {
3227  const auto expr = getArg(i);
3228  expr->collect_rte_idx(rte_idx_set);
3229  }
3230 }
3231 
3233  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3234  bool include_agg) const {
3235  for (auto p : expr_pair_list) {
3236  p.first->collect_column_var(colvar_set, include_agg);
3237  p.second->collect_column_var(colvar_set, include_agg);
3238  }
3239  if (else_expr != nullptr) {
3240  else_expr->collect_column_var(colvar_set, include_agg);
3241  }
3242 }
3243 
3245  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3246  bool include_agg) const {
3247  from_expr_->collect_column_var(colvar_set, include_agg);
3248 }
3249 
3251  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3252  bool include_agg) const {
3253  number_->collect_column_var(colvar_set, include_agg);
3254  datetime_->collect_column_var(colvar_set, include_agg);
3255 }
3256 
3258  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3259  bool include_agg) const {
3260  start_->collect_column_var(colvar_set, include_agg);
3261  end_->collect_column_var(colvar_set, include_agg);
3262 }
3263 
3265  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3266  bool include_agg) const {
3267  from_expr_->collect_column_var(colvar_set, include_agg);
3268 }
3269 
3271  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3272  bool include_agg) const {
3273  for (unsigned i = 0; i < getElementCount(); i++) {
3274  const auto expr = getElement(i);
3275  expr->collect_column_var(colvar_set, include_agg);
3276  }
3277 }
3278 
3280  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3281  bool include_agg) const {
3282  for (const auto& arg : args_) {
3283  arg->collect_column_var(colvar_set, include_agg);
3284  }
3285 }
3286 
3288  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3289  bool include_agg) const {
3290  for (unsigned i = 0; i < getArity(); i++) {
3291  const auto expr = getArg(i);
3292  expr->collect_column_var(colvar_set, include_agg);
3293  }
3294 }
3295 
3297  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
3298  for (auto p : expr_pair_list) {
3299  p.first->check_group_by(groupby);
3300  p.second->check_group_by(groupby);
3301  }
3302  if (else_expr != nullptr) {
3303  else_expr->check_group_by(groupby);
3304  }
3305 }
3306 
3308  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
3309  from_expr_->check_group_by(groupby);
3310 }
3311 
3313  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
3314  number_->check_group_by(groupby);
3315  datetime_->check_group_by(groupby);
3316 }
3317 
3319  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
3320  start_->check_group_by(groupby);
3321  end_->check_group_by(groupby);
3322 }
3323 
3325  const std::list<std::shared_ptr<Analyzer::Expr>>& groupby) const {
3326  from_expr_->check_group_by(groupby);
3327 }
3328 
3329 void CaseExpr::get_domain(DomainSet& domain_set) const {
3330  for (const auto& p : expr_pair_list) {
3331  const auto c = std::dynamic_pointer_cast<const Constant>(p.second);
3332  if (c != nullptr) {
3333  c->add_unique(domain_set);
3334  } else {
3335  const auto v = std::dynamic_pointer_cast<const ColumnVar>(p.second);
3336  if (v != nullptr) {
3337  v->add_unique(domain_set);
3338  } else {
3339  const auto cast = std::dynamic_pointer_cast<const UOper>(p.second);
3340  if (cast != nullptr && cast->get_optype() == kCAST) {
3341  const Constant* c = dynamic_cast<const Constant*>(cast->get_operand());
3342  if (c != nullptr) {
3343  cast->add_unique(domain_set);
3344  continue;
3345  } else {
3346  const auto v = std::dynamic_pointer_cast<const ColumnVar>(p.second);
3347  if (v != nullptr) {
3348  v->add_unique(domain_set);
3349  continue;
3350  }
3351  }
3352  }
3353  p.second->get_domain(domain_set);
3354  if (domain_set.empty()) {
3355  return;
3356  }
3357  }
3358  }
3359  }
3360  if (else_expr != nullptr) {
3361  const auto c = std::dynamic_pointer_cast<const Constant>(else_expr);
3362  if (c != nullptr) {
3363  c->add_unique(domain_set);
3364  } else {
3365  const auto v = std::dynamic_pointer_cast<const ColumnVar>(else_expr);
3366  if (v != nullptr) {
3367  v->add_unique(domain_set);
3368  } else {
3369  const auto cast = std::dynamic_pointer_cast<const UOper>(else_expr);
3370  if (cast != nullptr && cast->get_optype() == kCAST) {
3371  const Constant* c = dynamic_cast<const Constant*>(cast->get_operand());
3372  if (c != nullptr) {
3373  c->add_unique(domain_set);
3374  } else {
3375  const auto v = std::dynamic_pointer_cast<const ColumnVar>(else_expr);
3376  if (v != nullptr) {
3377  v->add_unique(domain_set);
3378  }
3379  }
3380  } else {
3381  else_expr->get_domain(domain_set);
3382  }
3383  }
3384  }
3385  }
3386 }
3387 
3388 std::shared_ptr<Analyzer::Expr> StringOper::deep_copy() const {
3389  std::vector<std::shared_ptr<Analyzer::Expr>> args_copy;
3390  for (const auto& arg : args_) {
3391  args_copy.emplace_back(arg->deep_copy());
3392  }
3393  std::vector<std::shared_ptr<Analyzer::Expr>> chained_string_op_exprs_copy;
3394  for (const auto& chained_string_op_expr : chained_string_op_exprs_) {
3395  chained_string_op_exprs_copy.emplace_back(chained_string_op_expr->deep_copy());
3396  }
3397  return makeExpr<Analyzer::StringOper>(
3398  kind_, std::move(args_copy), std::move(chained_string_op_exprs_copy));
3399 }
3400 
3401 std::shared_ptr<Analyzer::Expr> LowerStringOper::deep_copy() const {
3402  return makeExpr<Analyzer::LowerStringOper>(
3403  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3404 }
3405 
3406 std::shared_ptr<Analyzer::Expr> UpperStringOper::deep_copy() const {
3407  return makeExpr<Analyzer::UpperStringOper>(
3408  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3409 }
3410 
3411 std::shared_ptr<Analyzer::Expr> InitCapStringOper::deep_copy() const {
3412  return makeExpr<Analyzer::InitCapStringOper>(
3413  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3414 }
3415 
3416 std::shared_ptr<Analyzer::Expr> ReverseStringOper::deep_copy() const {
3417  return makeExpr<Analyzer::ReverseStringOper>(
3418  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3419 }
3420 
3421 std::shared_ptr<Analyzer::Expr> RepeatStringOper::deep_copy() const {
3422  return makeExpr<Analyzer::RepeatStringOper>(
3423  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3424 }
3425 
3426 std::shared_ptr<Analyzer::Expr> PadStringOper::deep_copy() const {
3427  return makeExpr<Analyzer::PadStringOper>(
3428  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3429 }
3430 
3431 std::shared_ptr<Analyzer::Expr> TrimStringOper::deep_copy() const {
3432  return makeExpr<Analyzer::TrimStringOper>(
3433  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3434 }
3435 
3436 std::shared_ptr<Analyzer::Expr> SubstringStringOper::deep_copy() const {
3437  return makeExpr<Analyzer::SubstringStringOper>(
3438  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3439 }
3440 
3441 std::shared_ptr<Analyzer::Expr> ReplaceStringOper::deep_copy() const {
3442  return makeExpr<Analyzer::ReplaceStringOper>(
3443  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3444 }
3445 
3446 std::shared_ptr<Analyzer::Expr> OverlayStringOper::deep_copy() const {
3447  return makeExpr<Analyzer::OverlayStringOper>(
3448  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3449 }
3450 
3451 std::shared_ptr<Analyzer::Expr> ConcatStringOper::deep_copy() const {
3452  return makeExpr<Analyzer::ConcatStringOper>(
3453  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3454 }
3455 
3456 std::shared_ptr<Analyzer::Expr> SplitPartStringOper::deep_copy() const {
3457  return makeExpr<Analyzer::SplitPartStringOper>(
3458  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3459 }
3460 
3461 std::shared_ptr<Analyzer::Expr> RegexpReplaceStringOper::deep_copy() const {
3462  return makeExpr<Analyzer::RegexpReplaceStringOper>(
3463  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3464 }
3465 
3466 std::shared_ptr<Analyzer::Expr> RegexpSubstrStringOper::deep_copy() const {
3467  return makeExpr<Analyzer::RegexpSubstrStringOper>(
3468  std::dynamic_pointer_cast<Analyzer::StringOper>(StringOper::deep_copy()));
3469 }
3470 
3471 std::shared_ptr<Analyzer::Expr> FunctionOper::deep_copy() const {
3472  std::vector<std::shared_ptr<Analyzer::Expr>> args_copy;
3473  for (size_t i = 0; i < getArity(); ++i) {
3474  args_copy.push_back(getArg(i)->deep_copy());
3475  }
3476  return makeExpr<Analyzer::FunctionOper>(type_info, getName(), args_copy);
3477 }
3478 
3479 bool StringOper::operator==(const Expr& rhs) const {
3480  const auto rhs_string_oper = dynamic_cast<const StringOper*>(&rhs);
3481 
3482  if (!rhs_string_oper) {
3483  return false;
3484  }
3485 
3486  if (get_kind() != rhs_string_oper->get_kind()) {
3487  return false;
3488  }
3489  if (getArity() != rhs_string_oper->getArity()) {
3490  return false;
3491  }
3492 
3493  for (size_t i = 0; i < getArity(); ++i) {
3494  if (!(*getArg(i) == *(rhs_string_oper->getArg(i)))) {
3495  return false;
3496  }
3497  }
3498  if (chained_string_op_exprs_.size() !=
3499  rhs_string_oper->chained_string_op_exprs_.size()) {
3500  return false;
3501  }
3502  for (size_t i = 0; i < chained_string_op_exprs_.size(); ++i) {
3503  if (!(*(chained_string_op_exprs_[i]) ==
3504  *(rhs_string_oper->chained_string_op_exprs_[i]))) {
3505  return false;
3506  }
3507  }
3508  return true;
3509 }
3510 
3511 bool FunctionOper::operator==(const Expr& rhs) const {
3512  if (type_info != rhs.get_type_info()) {
3513  return false;
3514  }
3515  const auto rhs_func_oper = dynamic_cast<const FunctionOper*>(&rhs);
3516  if (!rhs_func_oper) {
3517  return false;
3518  }
3519  if (getName() != rhs_func_oper->getName()) {
3520  return false;
3521  }
3522  if (getArity() != rhs_func_oper->getArity()) {
3523  return false;
3524  }
3525  for (size_t i = 0; i < getArity(); ++i) {
3526  if (!(*getArg(i) == *(rhs_func_oper->getArg(i)))) {
3527  return false;
3528  }
3529  }
3530  return true;
3531 }
3532 
3533 std::string StringOper::toString() const {
3534  std::string str{"(" + ::toString(kind_) + " "};
3535  for (const auto& arg : args_) {
3536  str += arg->toString();
3537  }
3538  str += ")";
3539  return str;
3540 }
3541 
3542 std::string FunctionOper::toString() const {
3543  std::string str{"(" + name_ + " "};
3544  for (const auto& arg : args_) {
3545  str += arg->toString();
3546  }
3547  str += ")";
3548  return str;
3549 }
3550 
3551 std::shared_ptr<Analyzer::Expr> FunctionOperWithCustomTypeHandling::deep_copy() const {
3552  std::vector<std::shared_ptr<Analyzer::Expr>> args_copy;
3553  for (size_t i = 0; i < getArity(); ++i) {
3554  args_copy.push_back(getArg(i)->deep_copy());
3555  }
3556  return makeExpr<Analyzer::FunctionOperWithCustomTypeHandling>(
3557  type_info, getName(), args_copy);
3558 }
3559 
3561  if (type_info != rhs.get_type_info()) {
3562  return false;
3563  }
3564  const auto rhs_func_oper =
3565  dynamic_cast<const FunctionOperWithCustomTypeHandling*>(&rhs);
3566  if (!rhs_func_oper) {
3567  return false;
3568  }
3569  if (getName() != rhs_func_oper->getName()) {
3570  return false;
3571  }
3572  if (getArity() != rhs_func_oper->getArity()) {
3573  return false;
3574  }
3575  for (size_t i = 0; i < getArity(); ++i) {
3576  if (!(*getArg(i) == *(rhs_func_oper->getArg(i)))) {
3577  return false;
3578  }
3579  }
3580  return true;
3581 }
3582 
3583 double WidthBucketExpr::get_bound_val(const Analyzer::Expr* bound_expr) const {
3584  CHECK(bound_expr);
3585  auto copied_expr = bound_expr->deep_copy();
3586  auto casted_expr = copied_expr->add_cast(SQLTypeInfo(kDOUBLE, false));
3587  CHECK(casted_expr);
3588  auto casted_constant = std::dynamic_pointer_cast<const Analyzer::Constant>(casted_expr);
3589  CHECK(casted_constant);
3590  return casted_constant->get_constval().doubleval;
3591 }
3592 
3594  auto const_partition_count_expr =
3595  dynamic_cast<const Analyzer::Constant*>(partition_count_.get());
3596  if (!const_partition_count_expr) {
3597  return -1;
3598  }
3599  auto d = const_partition_count_expr->get_constval();
3600  switch (const_partition_count_expr->get_type_info().get_type()) {
3601  case kTINYINT:
3602  return d.tinyintval;
3603  case kSMALLINT:
3604  return d.smallintval;
3605  case kINT:
3606  return d.intval;
3607  case kBIGINT: {
3608  auto bi = d.bigintval;
3609  if (bi < 1 || bi > INT32_MAX) {
3610  return -1;
3611  }
3612  return bi;
3613  }
3614  default:
3615  return -1;
3616  }
3617 }
3618 
3619 namespace {
3620 
3622  CHECK(geo);
3623  switch (geo->getType()) {
3625  return kPOINT;
3626  }
3628  return kLINESTRING;
3629  }
3631  return kPOLYGON;
3632  }
3634  return kMULTIPOLYGON;
3635  }
3636  default:
3637  UNREACHABLE();
3638  return kNULLT;
3639  }
3640 }
3641 
3642 } // namespace
3643 
3644 // TODO: fixup null
3645 GeoConstant::GeoConstant(std::unique_ptr<Geospatial::GeoBase>&& geo,
3646  const SQLTypeInfo& ti)
3647  : GeoExpr(ti), geo_(std::move(geo)) {
3648  CHECK(geo_);
3649  if (get_ti_from_geo(geo_.get()) != ti.get_type()) {
3650  throw std::runtime_error("Conflicting types for geo data " + geo_->getWktString() +
3651  " (type provided: " + ti.get_type_name() + ")");
3652  }
3653 }
3654 
3655 std::shared_ptr<Analyzer::Expr> GeoConstant::deep_copy() const {
3656  CHECK(geo_);
3657  return makeExpr<GeoConstant>(geo_->clone(), type_info);
3658 }
3659 
3660 std::string GeoConstant::toString() const {
3661  std::string str{"(GeoConstant "};
3662  CHECK(geo_);
3663  str += geo_->getWktString();
3664  str += ") ";
3665  return str;
3666 }
3667 
3668 std::string GeoConstant::getWKTString() const {
3669  CHECK(geo_);
3670  return geo_->getWktString();
3671 }
3672 
3673 bool GeoConstant::operator==(const Expr& rhs) const {
3674  if (typeid(rhs) != typeid(GeoConstant)) {
3675  return false;
3676  }
3677  const GeoConstant& rhs_c = dynamic_cast<const GeoConstant&>(rhs);
3678  if (type_info != rhs_c.get_type_info() /*|| is_null != rhs_c.get_is_null()*/) {
3679  return false;
3680  }
3681  /* TODO: constant nulls
3682  if (is_null && rhs_c.get_is_null()) {
3683  return true;
3684  }
3685 
3686  */
3687  return *geo_ == *rhs_c.geo_;
3688 }
3689 
3693 }
3694 
3695 std::shared_ptr<Analyzer::Constant> GeoConstant::makePhysicalConstant(
3696  const size_t index) const {
3697  // TODO: handle bounds, etc
3698  const auto num_phys_coords = type_info.get_physical_coord_cols();
3699  CHECK_GE(num_phys_coords, 0);
3700  CHECK_LE(index, size_t(num_phys_coords));
3701  SQLTypeInfo ti = type_info;
3702 
3703  std::vector<double> coords;
3704  std::vector<double> bounds;
3705  std::vector<int> ring_sizes;
3706  std::vector<int> poly_rings;
3707 
3709  geo_->getWktString(), ti, coords, bounds, ring_sizes, poly_rings);
3710 
3711  switch (index) {
3712  case 0: // coords
3713  return Geospatial::convert_coords(coords, ti);
3714  case 1: // ring sizes
3715  return Geospatial::convert_rings(ring_sizes);
3716  case 2: // poly rings
3717  return Geospatial::convert_rings(poly_rings);
3718  default:
3719  UNREACHABLE();
3720  }
3721 
3722  UNREACHABLE();
3723  return nullptr;
3724 }
3725 
3726 std::shared_ptr<Analyzer::Expr> GeoConstant::add_cast(const SQLTypeInfo& new_type_info) {
3727  // TODO: we should eliminate the notion of input and output SRIDs on a type. A type can
3728  // only have 1 SRID. A cast or transforms changes the SRID of the type.
3729  // NOTE: SRID 0 indicates set srid, skip cast
3730  SQLTypeInfo cast_type_info = new_type_info;
3731  if (!(get_type_info().get_input_srid() == 0) &&
3732  (get_type_info().get_input_srid() != new_type_info.get_output_srid())) {
3733  // run cast
3734  CHECK(geo_);
3735  if (!geo_->transform(get_type_info().get_input_srid(),
3736  new_type_info.get_output_srid())) {
3737  throw std::runtime_error("Failed to transform constant geometry: " + toString());
3738  }
3739  // The geo constant has been transformed but the new type info still encodes
3740  // a transform. Need to reset it and eliminate srid transition.
3741  cast_type_info.set_input_srid(new_type_info.get_output_srid());
3742  }
3743  return makeExpr<GeoConstant>(std::move(geo_), cast_type_info);
3744 }
3745 
3747  const std::string& name,
3748  const std::vector<std::shared_ptr<Analyzer::Expr>>& args,
3749  const std::optional<int>& output_srid_override)
3750  : GeoExpr(ti)
3751  , name_(name)
3752  , args_(args)
3753  , output_srid_override_(output_srid_override) {}
3754 
3755 std::shared_ptr<Analyzer::Expr> GeoOperator::deep_copy() const {
3756  std::vector<std::shared_ptr<Analyzer::Expr>> args;
3757  for (size_t i = 0; i < args_.size(); i++) {
3758  args.push_back(args_[i]->deep_copy());
3759  }
3760  return makeExpr<GeoOperator>(type_info, name_, args, output_srid_override_);
3761 }
3762 
3763 void GeoOperator::collect_rte_idx(std::set<int>& rte_idx_set) const {
3764  for (size_t i = 0; i < size(); i++) {
3765  const auto expr = getOperand(i);
3766  expr->collect_rte_idx(rte_idx_set);
3767  }
3768 }
3769 
3771  std::set<const ColumnVar*, bool (*)(const ColumnVar*, const ColumnVar*)>& colvar_set,
3772  bool include_agg) const {
3773  for (size_t i = 0; i < size(); i++) {
3774  const auto expr = getOperand(i);
3775  expr->collect_column_var(colvar_set, include_agg);
3776  }
3777 }
3778 
3779 std::string GeoOperator::toString() const {
3780  std::string str{"(" + name_ + " "};
3781  for (const auto& arg : args_) {
3782  str += arg->toString();
3783  }
3784  str += ")";
3785  return str;
3786 }
3787 
3788 bool GeoOperator::operator==(const Expr& rhs) const {
3789  if (typeid(rhs) != typeid(GeoOperator)) {
3790  return false;
3791  }
3792  const GeoOperator& rhs_go = dynamic_cast<const GeoOperator&>(rhs);
3793  if (getName() != rhs_go.getName()) {
3794  return false;
3795  }
3796  if (rhs_go.size() != size()) {
3797  return false;
3798  }
3799  for (size_t i = 0; i < size(); i++) {
3800  if (args_[i].get() != rhs_go.getOperand(i)) {
3801  return false;
3802  }
3803  }
3804  return true;
3805 }
3806 
3807 size_t GeoOperator::size() const {
3808  return args_.size();
3809 }
3810 
3811 Analyzer::Expr* GeoOperator::getOperand(const size_t index) const {
3812  CHECK_LT(index, args_.size());
3813  return args_[index].get();
3814 }
3815 
3816 std::shared_ptr<Analyzer::Expr> GeoOperator::add_cast(const SQLTypeInfo& new_type_info) {
3817  if (get_type_info().is_geometry()) {
3818  std::vector<std::shared_ptr<Analyzer::Expr>> args;
3819  for (size_t i = 0; i < args_.size(); i++) {
3820  args.push_back(args_[i]->deep_copy());
3821  }
3822  CHECK(new_type_info.is_geometry());
3823  return makeExpr<GeoOperator>(new_type_info, name_, args, output_srid_override_);
3824  } else {
3825  auto new_expr = deep_copy();
3826  return makeExpr<UOper>(new_type_info, /*contains_agg=*/false, kCAST, new_expr);
3827  }
3828 }
3829 
3830 std::shared_ptr<Analyzer::Expr> GeoTransformOperator::deep_copy() const {
3831  std::vector<std::shared_ptr<Analyzer::Expr>> args;
3832  for (size_t i = 0; i < args_.size(); i++) {
3833  args.push_back(args_[i]->deep_copy());
3834  }
3835  return makeExpr<GeoTransformOperator>(
3837 }
3838 
3839 std::string GeoTransformOperator::toString() const {
3840  std::string str{"(" + name_ + " "};
3841  for (const auto& arg : args_) {
3842  str += arg->toString();
3843  }
3844  str +=
3845  " : " + std::to_string(input_srid_) + " -> " + std::to_string(output_srid_) + " ";
3846  str += ")";
3847  return str;
3848 }
3849 
3850 bool GeoTransformOperator::operator==(const Expr& rhs) const {
3851  if (typeid(rhs) != typeid(GeoTransformOperator)) {
3852  return false;
3853  }
3854  const GeoTransformOperator& rhs_gto = dynamic_cast<const GeoTransformOperator&>(rhs);
3855  if (getName() != rhs_gto.getName()) {
3856  return false;
3857  }
3858  if (rhs_gto.size() != size()) {
3859  return false;
3860  }
3861  for (size_t i = 0; i < size(); i++) {
3862  if (args_[i].get() != rhs_gto.getOperand(i)) {
3863  return false;
3864  }
3865  }
3866  if (input_srid_ != rhs_gto.input_srid_) {
3867  return false;
3868  }
3869  if (output_srid_ != rhs_gto.output_srid_) {
3870  return false;
3871  }
3872  return true;
3873 }
3874 
3876  auto comparator = Analyzer::ColumnVar::colvar_comp;
3877  std::set<const Analyzer::ColumnVar*,
3878  bool (*)(const Analyzer::ColumnVar*, const Analyzer::ColumnVar*)>
3879  colvar_set(comparator);
3880  collect_column_var(colvar_set, true);
3881  if (colvar_set.size() != 1UL) {
3882  return false;
3883  }
3884  auto col_expr_ptr = *colvar_set.begin();
3885  CHECK(col_expr_ptr);
3886  return col_expr_ptr->get_type_info().is_dict_encoded_string();
3887 }
3888 
3889 std::vector<size_t> StringOper::getLiteralArgIndexes() const {
3890  std::vector<size_t> literal_arg_indexes;
3891  const auto num_args = args_.size();
3892  for (size_t idx = 0; idx < num_args; ++idx) {
3893  if (dynamic_cast<const Constant*>(args_[idx].get())) {
3894  literal_arg_indexes.emplace_back(idx);
3895  }
3896  }
3897  return literal_arg_indexes;
3898 }
3899 
3900 using LiteralArgMap = std::map<size_t, std::pair<SQLTypes, Datum>>;
3901 
3903  LiteralArgMap literal_arg_map;
3904  const auto num_args = getArity();
3905  for (size_t idx = 0; idx < num_args; ++idx) {
3906  const auto constant_arg_expr = dynamic_cast<const Analyzer::Constant*>(getArg(idx));
3907  if (constant_arg_expr) {
3908  literal_arg_map.emplace(
3909  std::make_pair(idx,
3910  std::make_pair(constant_arg_expr->get_type_info().get_type(),
3911  constant_arg_expr->get_constval())));
3912  }
3913  }
3914  return literal_arg_map;
3915 }
3916 
3918  const std::vector<std::shared_ptr<Analyzer::Expr>> args) {
3919  if (args.empty()) {
3920  return SQLTypeInfo(kNULLT);
3921  }
3922  // Constant literal first argument
3923  if (dynamic_cast<const Analyzer::Constant*>(args[0].get())) {
3924  return args[0]->get_type_info();
3925  }
3926  // None-encoded text column argument
3927  // Note that whether or not this is allowed is decided separately
3928  // in check_operand_types
3929  if (args[0]->get_type_info().is_none_encoded_string()) {
3930  return SQLTypeInfo(kTEXT, kENCODING_DICT, 0, kNULLT);
3931  }
3932  // If here, we have a dict-encoded column arg
3933  SQLTypeInfo ret_ti(args[0]->get_type_info());
3934  // Set return as nullable as string op can create nulls
3935  ret_ti.set_notnull(false);
3936  return ret_ti;
3937 }
3938 
3940  const size_t min_args,
3941  const std::vector<OperandTypeFamily>& expected_type_families,
3942  const std::vector<std::string>& arg_names,
3943  const bool dict_encoded_cols_only,
3944  const bool cols_first_arg_only) const {
3945  std::ostringstream oss;
3947  oss << "Function " << ::toString(get_kind()) << " not supported.";
3948  throw std::runtime_error(oss.str());
3949  }
3950  const size_t num_args = args_.size();
3951  CHECK_EQ(expected_type_families.size(), arg_names.size());
3952  if (num_args < min_args || num_args > expected_type_families.size()) {
3953  oss << "Error instantiating " << ::toString(get_kind()) << " operator. ";
3954  oss << "Expected " << expected_type_families.size() << " arguments, but received "
3955  << num_args << ".";
3956  }
3957  for (size_t arg_idx = 0; arg_idx < num_args; ++arg_idx) {
3958  const auto& expected_type_family = expected_type_families[arg_idx];
3959  // We need to remove any casts that Calcite may add to try the right operand type,
3960  // even if we don't support them. Need to check how this works with casts we do
3961  // support.
3962  auto arg_ti = args_[arg_idx]->get_type_info();
3963  const auto decasted_arg = remove_cast(args_[arg_idx]);
3964  const bool is_arg_constant =
3965  dynamic_cast<const Analyzer::Constant*>(decasted_arg.get()) != nullptr;
3966  const bool is_arg_column_var =
3967  dynamic_cast<const Analyzer::ColumnVar*>(decasted_arg.get()) != nullptr;
3968  const bool is_arg_string_oper =
3969  dynamic_cast<const Analyzer::StringOper*>(decasted_arg.get()) != nullptr;
3970  if (!(is_arg_constant || is_arg_column_var || is_arg_string_oper)) {
3971  oss << "Error instantiating " << ::toString(get_kind()) << " operator. "
3972  << "Currently only constant, column, or other string operator arguments "
3973  << "are allowed as inputs.";
3974  throw std::runtime_error(oss.str());
3975  }
3976  auto decasted_arg_ti = decasted_arg->get_type_info();
3977  // We need to prevent any non-string type from being casted to a string, but can
3978  // permit non-integer types being casted to integers Todo: Find a cleaner way to
3979  // handle this (we haven't validated any of the casts that calcite has given us at the
3980  // point of RelAlgTranslation)
3981  if (arg_ti != decasted_arg_ti &&
3982  ((arg_ti.is_string() && !decasted_arg_ti.is_string()) ||
3983  (arg_ti.is_integer() && decasted_arg_ti.is_string()))) {
3984  arg_ti = decasted_arg_ti;
3985  }
3986 
3987  if (cols_first_arg_only && !is_arg_constant && arg_idx >= 1UL) {
3988  oss << "Error instantiating " << ::toString(get_kind()) << " operator. "
3989  << "Currently only column inputs allowed for the primary argument, "
3990  << "but a column input was received for argument " << arg_idx + 1 << ".";
3991  throw std::runtime_error(oss.str());
3992  }
3993  switch (expected_type_family) {
3995  if (!arg_ti.is_string()) {
3996  oss << "Error instantiating " << ::toString(get_kind()) << " operator. "
3997  << "Expected text type for argument " << arg_idx + 1 << " ("
3998  << arg_names[arg_idx] << ").";
3999  throw std::runtime_error(oss.str());
4000  break;
4001  }
4002  if (dict_encoded_cols_only &&
4003  (!is_arg_constant && !arg_ti.is_dict_encoded_string())) {
4004  oss << "Error instantiating " << ::toString(get_kind()) << " operator. "
4005  << "Currently only text-encoded dictionary-encoded column inputs are "
4006  << "allowed, but a none-encoded text column argument was received.";
4007  throw std::runtime_error(oss.str());
4008  break;
4009  }
4010  break;
4011  }
4013  if (!IS_INTEGER(arg_ti.get_type())) {
4014  oss << "Error instantiating " << ::toString(get_kind()) << " operator. "
4015  << "Expected integer type for argument " << arg_idx + 1 << " ("
4016  << arg_names[arg_idx] << ").";
4017  throw std::runtime_error(oss.str());
4018  break;
4019  }
4020  if (!is_arg_constant) {
4021  oss << "Error instantiating " << ::toString(get_kind()) << " operator. "
4022  << "Currently only text-encoded dictionary column inputs are "
4023  << "allowed, but an integer-type column was provided.";
4024  throw std::runtime_error(oss.str());
4025  break;
4026  }
4027  break;
4028  }
4029  }
4030  }
4031 }
4032 
4034  const std::vector<std::shared_ptr<Analyzer::Expr>>& operands) {
4035  if (operands.size() != 2UL) {
4036  std::ostringstream oss;
4037  oss << "Concat operator expects two arguments, but was provided " << operands.size()
4038  << ".";
4039  throw std::runtime_error(oss.str());
4040  }
4041  if (operands[1].get()->get_type_info().is_dict_encoded_string() &&
4042  !(operands[0].get()->get_type_info().is_dict_encoded_string())) {
4043  return SqlStringOpKind::RCONCAT;
4044  }
4045  return SqlStringOpKind::CONCAT;
4046 }
4047 
4048 std::vector<std::shared_ptr<Analyzer::Expr>> ConcatStringOper::normalize_operands(
4049  const std::vector<std::shared_ptr<Analyzer::Expr>>& operands) {
4051  CHECK_EQ(operands.size(), 2UL); // Size should be 2 per get_concat_ordered_kind
4052  return {operands[1], operands[0]};
4053  }
4054  return operands;
4055 }
4056 
4058  const SqlStringOpKind pad_op_kind) {
4059  if (!(pad_op_kind == SqlStringOpKind::LPAD || pad_op_kind == SqlStringOpKind::RPAD)) {
4060  // Arguably should CHECK here
4061  throw std::runtime_error("Invalid pad type supplied to PAD operator");
4062  }
4063  return pad_op_kind;
4064 }
4065 
4067  const SqlStringOpKind trim_op_kind_maybe,
4068  const std::vector<std::shared_ptr<Analyzer::Expr>>& args) {
4069  auto get_trim_type_if_exists = [&args]() {
4070  if (args.empty()) {
4071  return SqlStringOpKind::INVALID;
4072  }
4073  const auto trim_type_arg = dynamic_cast<const Analyzer::Constant*>(args[0].get());
4074  if (!trim_type_arg) {
4075  return SqlStringOpKind::INVALID;
4076  }
4077  const auto trim_type_str = to_upper(*trim_type_arg->get_constval().stringval);
4078  if (trim_type_str == "BOTH") {
4079  return SqlStringOpKind::TRIM;
4080  }
4081  if (trim_type_str == "LEADING") {
4082  return SqlStringOpKind::LTRIM;
4083  }
4084  if (trim_type_str == "TRAILING") {
4085  return SqlStringOpKind::RTRIM;
4086  }
4087  return SqlStringOpKind::INVALID;
4088  };
4089 
4090  const auto trim_op_kind = trim_op_kind_maybe == SqlStringOpKind::TRIM
4091  ? get_trim_type_if_exists()
4092  : trim_op_kind_maybe;
4094  return trim_op_kind;
4095 }
4096 
4097 std::vector<std::shared_ptr<Analyzer::Expr>> TrimStringOper::normalize_operands(
4098  const std::vector<std::shared_ptr<Analyzer::Expr>>& operands,
4099  const SqlStringOpKind string_op_kind) {
4100  if (operands.size() < 2UL) {
4101  throw std::runtime_error("Trim operator expects 2 arguments.");
4102  }
4103 
4104  // Calcite is returning LTRIM/RTRIM(string_literal1, string_literal2) with the
4105  // arguments in that order, but LTRIM/TRIM(string_var, string_literal) in the
4106  // reverse order that the main TRIM operator uses as well
4107  // Until we can look into that more, reverse order only if we have a const then
4108  // non-const input order
4109 
4110  if (string_op_kind == SqlStringOpKind::LTRIM ||
4111  string_op_kind == SqlStringOpKind::RTRIM) {
4112  CHECK_EQ(operands.size(), 2UL);
4113  if (dynamic_cast<const Analyzer::Constant*>(operands[0].get()) &&
4114  !dynamic_cast<const Analyzer::Constant*>(operands[1].get())) {
4115  return {operands[1], operands[0]};
4116  }
4117  return operands;
4118  }
4119  CHECK_EQ(operands.size(), 3UL);
4120  return {operands[2], operands[1]};
4121 }
4122 
4123 } // namespace Analyzer
4124 
4125 bool expr_list_match(const std::vector<std::shared_ptr<Analyzer::Expr>>& lhs,
4126  const std::vector<std::shared_ptr<Analyzer::Expr>>& rhs) {
4127  if (lhs.size() != rhs.size()) {
4128  return false;
4129  }
4130  for (size_t i = 0; i < lhs.size(); ++i) {
4131  if (!(*lhs[i] == *rhs[i])) {
4132  return false;
4133  }
4134  }
4135  return true;
4136 }
4137 
4138 std::shared_ptr<Analyzer::Expr> remove_cast(const std::shared_ptr<Analyzer::Expr>& expr) {
4139  const auto uoper = dynamic_cast<const Analyzer::UOper*>(expr.get());
4140  if (!uoper || uoper->get_optype() != kCAST) {
4141  return expr;
4142  }
4143  return uoper->get_own_operand();
4144 }
4145 
4147  const auto uoper = dynamic_cast<const Analyzer::UOper*>(expr);
4148  if (!uoper || uoper->get_optype() != kCAST) {
4149  return expr;
4150  }
4151  return uoper->get_operand();
4152 }
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:3146
std::shared_ptr< Analyzer::Expr > arg
Definition: Analyzer.h:1174
int8_t tinyintval
Definition: sqltypes.h:212
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3551
int get_table_id() const
Definition: Analyzer.h:200
std::shared_ptr< Analyzer::Expr > arg
Definition: Analyzer.h:1016
Query * next_query
Definition: Analyzer.h:2484
Defines data structures for the semantic analysis phase of query processing.
InIntegerSet(const std::shared_ptr< const Analyzer::Expr > a, const std::vector< int64_t > &values, const bool not_null)
Definition: Analyzer.cpp:1618
Definition: sqldefs.h:71
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1967
HOST DEVICE SQLTypes get_subtype() const
Definition: sqltypes.h:330
void set_compression(EncodingType c)
Definition: sqltypes.h:440
T roundDecimal(int64_t n, unsigned scale)
Definition: Analyzer.cpp:778
std::string toString() const override
Definition: Analyzer.cpp:2793
Query * parsetree
Definition: Analyzer.h:626
double power10(unsigned const x)
Definition: misc.h:270
float get_likelihood() const
Definition: Analyzer.h:1141
#define CHECK_EQ(x, y)
Definition: Logger.h:231
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2116
std::shared_ptr< Analyzer::Expr > expr
Definition: Analyzer.h:2403
std::string toString() const override
Definition: Analyzer.cpp:2715
bool unnest
Definition: Analyzer.h:2404
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1604
InValues(std::shared_ptr< Analyzer::Expr > a, const std::list< std::shared_ptr< Analyzer::Expr >> &l)
Definition: Analyzer.cpp:1600
const Expr * get_from_expr() const
Definition: Analyzer.h:1304
static bool simple_predicate_has_simple_cast(const std::shared_ptr< Analyzer::Expr > cast_operand, const std::shared_ptr< Analyzer::Expr > const_operand)
Definition: Analyzer.cpp:1465
#define IS_LOGIC(X)
Definition: sqldefs.h:61
const Expr * get_partition_count() const
Definition: Analyzer.h:1043
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2454
std::string toString() const override
Definition: Analyzer.cpp:2544
#define NULL_DOUBLE
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:3121
GeoConstant(std::unique_ptr< Geospatial::GeoBase > &&geo, const SQLTypeInfo &ti)
Definition: Analyzer.cpp:3645
void get_domain(DomainSet &domain_set) const override
Definition: Analyzer.cpp:3329
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2138
std::string toString() const final
Definition: Analyzer.cpp:3660
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2240
const Expr * get_else_expr() const
Definition: Analyzer.h:1259
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3401
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2342
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:229
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:3511
bool Datum_equal(const SQLTypeInfo &ti, Datum val1, Datum val2)
Definition: Analyzer.cpp:2174
std::string DatumToString(Datum d, const SQLTypeInfo &ti)
Definition: Datum.cpp:392
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:3015
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2232
const Expr * get_escape_expr() const
Definition: Analyzer.h:906
std::shared_ptr< Analyzer::Expr > arg
Definition: Analyzer.h:792
std::shared_ptr< Analyzer::Expr > rewrite_with_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2045
std::shared_ptr< Analyzer::Expr > decompress()
Definition: Analyzer.cpp:692
size_t getArity() const
Definition: Analyzer.h:2169
std::optional< int > output_srid_override_
Definition: Analyzer.h:2608
Definition: sqltypes.h:49
std::shared_ptr< Analyzer::Expr > remove_cast(const std::shared_ptr< Analyzer::Expr > &expr)
Definition: Analyzer.cpp:4138
int64_t DateTruncate(DatetruncField field, const int64_t timeval)
bool is_null_value(const SQLTypeInfo &ti, const Datum &constval)
Definition: Analyzer.cpp:1156
static bool colvar_comp(const ColumnVar *l, const ColumnVar *r)
Definition: Analyzer.h:215
SQLTypes
Definition: sqltypes.h:38
void add_rte(RangeTableEntry *rte)
Definition: Analyzer.cpp:1418
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:3054
std::shared_ptr< Analyzer::Expr > operand
Definition: Analyzer.h:418
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3436
std::shared_ptr< Analyzer::Expr > arg
Definition: Analyzer.h:746
std::list< std::pair< std::shared_ptr< Analyzer::Expr >, std::shared_ptr< Analyzer::Expr > > > expr_pair_list
Definition: Analyzer.h:1286
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1785
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2102
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2471
#define NULL_FLOAT
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3388
void collect_rte_idx(std::set< int > &rte_idx_set) const final
Definition: Analyzer.cpp:3763
std::shared_ptr< Analyzer::Expr > rewrite_with_child_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2088
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2294
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1540
#define NULL_BIGINT
virtual void add_unique(std::list< const Expr * > &expr_list) const
Definition: Analyzer.cpp:2988
std::shared_ptr< Analyzer::Expr > right_operand
Definition: Analyzer.h:524
std::shared_ptr< Analyzer::Expr > escape_expr
Definition: Analyzer.h:1020
bool operator==(Expr const &rhs) const override
Definition: Analyzer.cpp:2490
ExtractField get_field() const
Definition: Analyzer.h:1303
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1908
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1637
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3219
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:142
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:104
void collect_column_var(std::set< const ColumnVar *, bool(*)(const ColumnVar *, const ColumnVar *)> &colvar_set, bool include_agg) const override
Definition: Analyzer.cpp:3287
bool is_fp() const
Definition: sqltypes.h:514
const Expr * get_escape_expr() const
Definition: Analyzer.h:978
HOST DEVICE int get_scale() const
Definition: sqltypes.h:334
const Expr * get_right_operand() const
Definition: Analyzer.h:450
SQLOps
Definition: sqldefs.h:29
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1751
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3198
std::string toString() const override
Definition: Analyzer.cpp:2936
Definition: sqldefs.h:35
std::map< size_t, std::pair< SQLTypes, Datum >> LiteralArgMap
Definition: Analyzer.h:1567
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3451
int8_t boolval
Definition: sqltypes.h:211
std::string get_compression_name() const
Definition: sqltypes.h:481
std::shared_ptr< Analyzer::Expr > arg
Definition: Analyzer.h:668
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:89
Definition: sqldefs.h:36
const std::vector< std::shared_ptr< Analyzer::Expr > > args0_
Definition: Analyzer.h:2347
SQLTypeInfo ti0_
Definition: Analyzer.h:2377
std::shared_ptr< Analyzer::Expr > like_expr
Definition: Analyzer.h:953
bool get_is_null() const
Definition: Analyzer.h:341
Definition: sqldefs.h:38
const std::vector< std::shared_ptr< Analyzer::Expr > > args0_
Definition: Analyzer.h:2379
std::string toString() const override
Definition: Analyzer.cpp:3542
VarlenDatum * arrayval
Definition: sqltypes.h:218
void collect_column_var(std::set< const ColumnVar *, bool(*)(const ColumnVar *, const ColumnVar *)> &colvar_set, bool include_agg) const override
Definition: Analyzer.cpp:3257
int tle_no
Definition: Analyzer.h:2232
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:150
const std::shared_ptr< const Analyzer::Expr > arg
Definition: Analyzer.h:697
#define UNREACHABLE()
Definition: Logger.h:267
const std::shared_ptr< Analyzer::Expr > get_own_operand() const
Definition: Analyzer.h:379
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:215
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:219
#define CHECK_GE(x, y)
Definition: Logger.h:236
void cast_from_string(const SQLTypeInfo &new_type_info)
Definition: Analyzer.cpp:1131
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3406
SqlStringOpKind
Definition: sqldefs.h:85
void check_group_by(const std::list< std::shared_ptr< Analyzer::Expr >> &groupby) const override
Definition: Analyzer.cpp:3324
std::string toString() const override
Definition: Analyzer.cpp:2757
Definition: sqldefs.h:49
Definition: sqldefs.h:30
std::shared_ptr< Analyzer::Expr > add_cast(const SQLTypeInfo &new_type_info) override
Definition: Analyzer.cpp:1375
std::shared_ptr< Analyzer::Expr > ExpressionPtr
Definition: Analyzer.h:186
const Geospatial::GeoBase::GeoOp op_
Definition: Analyzer.h:2376
const Expr * get_arg() const
Definition: Analyzer.h:975
size_t getArity() const
Definition: Analyzer.h:1506
const std::vector< std::shared_ptr< Analyzer::Expr > > order_keys_
Definition: Analyzer.h:2279
std::shared_ptr< Analyzer::Expr > rewrite_with_child_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2080
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:3479
Expr * get_arg() const
Definition: Analyzer.h:1202
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2397
DatetruncField get_field() const
Definition: Analyzer.h:1428
static SqlStringOpKind get_and_validate_trim_op_kind(const SqlStringOpKind trim_op_kind_maybe, const std::vector< std::shared_ptr< Analyzer::Expr >> &args)
Definition: Analyzer.cpp:4066
Definition: sqldefs.h:41
const Expr * get_arg() const
Definition: Analyzer.h:1139
bool is_expr_nullable(const Analyzer::Expr *expr)
Definition: Analyzer.cpp:1576
std::shared_ptr< Analyzer::Expr > upper_bound_
Definition: Analyzer.h:1123
Constants for Builtin SQL Types supported by OmniSci.
std::shared_ptr< Analyzer::Expr > add_cast(const SQLTypeInfo &new_type_info) override
Definition: Analyzer.cpp:1356
std::shared_ptr< Analyzer::Expr > arg
Definition: Analyzer.h:1236
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:3560
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3755
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:68
const std::vector< std::shared_ptr< Analyzer::Expr > > args_
Definition: Analyzer.h:2193
const std::vector< std::shared_ptr< Analyzer::Expr > > partition_keys_
Definition: Analyzer.h:2278
static std::vector< std::shared_ptr< Analyzer::Expr > > normalize_operands(const std::vector< std::shared_ptr< Analyzer::Expr >> &operands)
Definition: Analyzer.cpp:4048
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3446
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3212
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2376
HOST DEVICE SQLTypes get_type() const
Definition: sqltypes.h:329
~Constant() override
Definition: Analyzer.cpp:42
std::unique_ptr< Geospatial::GeoBase > geo_
Definition: Analyzer.h:2555
SQLQualifier qualifier
Definition: Analyzer.h:521
bool isNull() const
Definition: Analyzer.h:2304
std::shared_ptr< Analyzer::Expr > partition_count_
Definition: Analyzer.h:1124
std::string toString() const override
Definition: Analyzer.cpp:2872
bool is_number() const
Definition: sqltypes.h:515
constexpr int64_t get_datetime_scaled_epoch(const ScalingType direction, const int64_t epoch, const int32_t dimen)
std::string toString() const override
Definition: Analyzer.cpp:2605
SQLTypeInfo type_info
Definition: Analyzer.h:182
std::list< const Expr * > DomainSet
Definition: Analyzer.h:64
virtual void collect_column_var(std::set< const ColumnVar *, bool(*)(const ColumnVar *, const ColumnVar *)> &colvar_set, bool include_agg) const
Definition: Analyzer.h:119
int32_t intval
Definition: sqltypes.h:214
const Expr * get_arg() const
Definition: Analyzer.h:903
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:3087
bool is_time() const
Definition: sqltypes.h:516
std::string toString() const override
Definition: Analyzer.cpp:2553
void check_group_by(const std::list< std::shared_ptr< Analyzer::Expr >> &groupby) const override
Definition: Analyzer.cpp:1450
double get_bound_val(const Analyzer::Expr *bound_expr) const
Definition: Analyzer.cpp:3583
std::shared_ptr< Analyzer::Expr > rewrite_with_child_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2074
constexpr double f
Definition: Utm.h:31
std::string to_string(char const *&&v)
static SQLTypeInfo get_return_type(const std::vector< std::shared_ptr< Analyzer::Expr >> args)
Definition: Analyzer.cpp:3917
~Subquery() override
Definition: Analyzer.cpp:48
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2414
bool operator==(const Expr &) const override
Definition: Analyzer.cpp:3850
int get_rte_idx(const std::string &range_var_name) const
Definition: Analyzer.cpp:1407
void cast_string(const SQLTypeInfo &new_type_info)
Definition: Analyzer.cpp:1120
const std::vector< std::shared_ptr< Analyzer::Expr > > args_
Definition: Analyzer.h:2277
void check_group_by(const std::list< std::shared_ptr< Analyzer::Expr >> &groupby) const override
Definition: Analyzer.cpp:3307
std::string toString() const override
Definition: Analyzer.cpp:2574
std::vector< std::shared_ptr< Analyzer::Expr > > chained_string_op_exprs_
Definition: Analyzer.h:1618
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:78
#define NULL_INT
std::string toString() const override
Definition: Analyzer.cpp:2680
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3456
constexpr double a
Definition: Utm.h:32
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:2998
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2272
bool g_enable_string_functions
std::string toString() const override
Definition: Analyzer.cpp:2771
std::vector< size_t > getLiteralArgIndexes() const
Definition: Analyzer.cpp:3889
std::string toString() const override
Definition: Analyzer.cpp:2802
std::string toString() const override
Definition: Analyzer.cpp:2738
Definition: sqldefs.h:75
bool get_calc_encoded_length() const
Definition: Analyzer.h:712
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2249
std::shared_ptr< Analyzer::Expr > rewrite_with_child_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1958
std::string toString() const override
Definition: Analyzer.cpp:2913
DatetruncField field_
Definition: Analyzer.h:1454
std::shared_ptr< Analyzer::Expr > rewrite_with_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1922
const Geospatial::GeoBase::GeoOp op_
Definition: Analyzer.h:2345
std::string toString() const override
Definition: Analyzer.cpp:2890
SQLOps get_optype() const
Definition: Analyzer.h:446
std::shared_ptr< Analyzer::Expr > left_operand
Definition: Analyzer.h:523
This file contains the class specification and related data structures for Catalog.
void check_operand_types(const size_t min_args, const std::vector< OperandTypeFamily > &expected_type_families, const std::vector< std::string > &arg_names, const bool dict_encoded_cols_only=true, const bool cols_first_arg_only=true) const
Definition: Analyzer.cpp:3939
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2475
void set_input_srid(int d)
Definition: sqltypes.h:433
const std::vector< std::shared_ptr< Analyzer::Expr > > args1_
Definition: Analyzer.h:2380
float floatval
Definition: sqltypes.h:216
std::shared_ptr< Analyzer::Constant > arg1
Definition: Analyzer.h:1239
std::string toString() const
Definition: Analyzer.cpp:2966
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:117
std::shared_ptr< Analyzer::Expr > normalize_simple_predicate(int &rte_idx) const override
Definition: Analyzer.cpp:1489
const std::list< std::shared_ptr< Analyzer::Expr > > value_list
Definition: Analyzer.h:670
EncodingType
Definition: sqltypes.h:233
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:175
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:168
static SQLTypeInfo common_string_type(const SQLTypeInfo &type1, const SQLTypeInfo &type2)
Definition: Analyzer.cpp:415
std::shared_ptr< Analyzer::Expr > right_operand_
Definition: Analyzer.h:571
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1532
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:184
static SqlStringOpKind validate_trim_op_kind(const SqlStringOpKind trim_op_kind)
Definition: Analyzer.h:1884
bool hasSingleDictEncodedColInput() const
returns whether we have one and only one column involved in this StringOper and all its descendents...
Definition: Analyzer.cpp:3875
std::shared_ptr< Analyzer::Expr > deep_copy() const final
Definition: Analyzer.cpp:3655
LiteralArgMap getLiteralArgs() const
Definition: Analyzer.cpp:3902
std::string toString() const override
Definition: Analyzer.cpp:2669
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1999
const DatetruncField field_
Definition: Analyzer.h:1412
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1681
const std::vector< std::shared_ptr< Analyzer::Expr > > & getTuple() const
Definition: Analyzer.h:251
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3203
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:2122
bool is_castable(const SQLTypeInfo &new_type_info) const
Definition: sqltypes.h:606
void set_fixed_size()
Definition: sqltypes.h:438
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3194
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3225
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:3074
std::shared_ptr< Analyzer::Expr > lower_bound_
Definition: Analyzer.h:1122
bool is_integer() const
Definition: sqltypes.h:512
std::string toString() const override
Definition: Analyzer.cpp:2750
const DateaddField field_
Definition: Analyzer.h:1370
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:124
std::shared_ptr< Analyzer::Expr > from_expr_
Definition: Analyzer.h:1455
bool expr_list_match(const std::vector< std::shared_ptr< Analyzer::Expr >> &lhs, const std::vector< std::shared_ptr< Analyzer::Expr >> &rhs)
Definition: Analyzer.cpp:4125
void collect_column_var(std::set< const ColumnVar *, bool(*)(const ColumnVar *, const ColumnVar *)> &colvar_set, bool include_agg) const override
Definition: Analyzer.cpp:3270
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2707
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:200
std::string toString() const override
Definition: Analyzer.cpp:2538
void set_scale(int s)
Definition: sqltypes.h:434
int64_t bigintval
Definition: sqltypes.h:215
void check_group_by(const std::list< std::shared_ptr< Analyzer::Expr >> &groupby) const override
Definition: Analyzer.cpp:1438
const std::shared_ptr< Analyzer::Expr > end_
Definition: Analyzer.h:1414
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2437
std::string toString() const override
Definition: Analyzer.cpp:2782
WhichRow get_which_row() const
Definition: Analyzer.h:280
void check_group_by(const std::list< std::shared_ptr< Analyzer::Expr >> &groupby) const override
Definition: Analyzer.cpp:3312
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2362
const std::shared_ptr< Analyzer::Expr > number_
Definition: Analyzer.h:1371
const std::list< std::shared_ptr< Analyzer::Expr > > value_list
Definition: Analyzer.h:355
bool is_timeinterval() const
Definition: sqltypes.h:521
std::string resname
Definition: Analyzer.h:2402
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:3421
std::shared_ptr< Analyzer::Expr > deep_copy() const override
Definition: Analyzer.cpp:2703
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2445
const std::string & getName() const
Definition: Analyzer.h:2586
std::string toString() const override
Definition: Analyzer.cpp:2882
static SQLTypeInfo common_numeric_type(const SQLTypeInfo &type1, const SQLTypeInfo &type2)
Definition: Analyzer.cpp:455
void collect_rte_idx(std::set< int > &rte_idx_set) const override
Definition: Analyzer.cpp:3208
SQLTypeInfo ti1_
Definition: Analyzer.h:2378
std::shared_ptr< Analyzer::Expr > rewrite_with_targetlist(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1976
Definition: sqldefs.h:37
Definition: sqldefs.h:77
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1695
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2144
Definition: sqldefs.h:71
int16_t smallintval
Definition: sqltypes.h:213
const std::shared_ptr< Analyzer::Expr > start_
Definition: Analyzer.h:1413
int get_varno() const
Definition: Analyzer.h:282
std::string toString() const
Definition: Analyzer.cpp:2976
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1651
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1709
bool nulls_first
Definition: Analyzer.h:2234
std::shared_ptr< Analyzer::Expr > rewrite_agg_to_var(const std::vector< std::shared_ptr< TargetEntry >> &tlist) const override
Definition: Analyzer.cpp:1940
void collect_column_var(std::set< const ColumnVar *, bool(*)(const ColumnVar *, const ColumnVar *)> &colvar_set, bool include_agg) const override
Definition: Analyzer.cpp:3232
Datum StringToDatum(std::string_view s, SQLTypeInfo &ti)
Definition: Datum.cpp:275
bool get_is_distinct() const
Definition: Analyzer.h:1204
std::shared_ptr< Analyzer::Constant > convert_rings(const std::vector< int > &rings)
Definition: Conversion.h:44
bool is_boolean() const
Definition: sqltypes.h:517
static std::vector< std::shared_ptr< Analyzer::Expr > > normalize_operands(const std::vector< std::shared_ptr< Analyzer::Expr >> &operands, const SqlStringOpKind string_op_kind)
Definition: Analyzer.cpp:4097
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2260
const std::vector< OrderEntry > collation_
Definition: Analyzer.h:2280
const Expr * get_start_expr() const
Definition: Analyzer.h:1387
void do_cast(const SQLTypeInfo &new_type_info)
Definition: Analyzer.cpp:1200
std::string toString() const override
Definition: Analyzer.cpp:2560
void group_predicates(std::list< const Expr * > &scan_predicates, std::list< const Expr * > &join_predicates, std::list< const Expr * > &const_predicates) const override
Definition: Analyzer.cpp:1829
#define NULL_BOOLEAN
bool operator==(const Expr &rhs) const override
Definition: Analyzer.cpp:2522
void find_expr(bool(*f)(const Expr *), std::list< const Expr * > &expr_list) const override
Definition: Analyzer.cpp:31