OmniSciDB  94e8789169
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
Datum.cpp File Reference
#include <cassert>
#include <cstdio>
#include <cstdlib>
#include <stdexcept>
#include <string>
#include "DateConverters.h"
#include "DateTimeParser.h"
#include "Logger/Logger.h"
#include "QueryEngine/DateTimeUtils.h"
#include "StringTransform.h"
#include "misc.h"
#include "sqltypes.h"
+ Include dependency graph for Datum.cpp:

Go to the source code of this file.

Functions

int64_t parse_numeric (const std::string_view s, SQLTypeInfo &ti)
 
Datum StringToDatum (std::string_view s, SQLTypeInfo &ti)
 
bool DatumEqual (const Datum a, const Datum b, const SQLTypeInfo &ti)
 
std::string DatumToString (Datum d, const SQLTypeInfo &ti)
 
SQLTypes decimal_to_int_type (const SQLTypeInfo &ti)
 
int64_t convert_decimal_value_to_scale (const int64_t decimal_value, const SQLTypeInfo &type_info, const SQLTypeInfo &new_type_info)
 

Function Documentation

int64_t convert_decimal_value_to_scale ( const int64_t  decimal_value,
const SQLTypeInfo type_info,
const SQLTypeInfo new_type_info 
)

Definition at line 319 of file Datum.cpp.

References SQLTypeInfo::get_scale(), and generate_TableFunctionsFactory_init::i.

Referenced by import_export::TypedImportBuffer::add_value(), Analyzer::Constant::cast_number(), anonymous_namespace{ArrowImporter.h}::ArrowValue< arrow::Decimal128 >::operator const DATA_TYPE(), and anonymous_namespace{TypedDataAccessors.h}::put_scalar().

321  {
322  auto converted_decimal_value = decimal_value;
323  if (new_type_info.get_scale() > type_info.get_scale()) {
324  for (int i = 0; i < new_type_info.get_scale() - type_info.get_scale(); i++) {
325  converted_decimal_value *= 10;
326  }
327  } else if (new_type_info.get_scale() < type_info.get_scale()) {
328  for (int i = 0; i < type_info.get_scale() - new_type_info.get_scale(); i++) {
329  if (converted_decimal_value > 0) {
330  converted_decimal_value = (converted_decimal_value + 5) / 10;
331  } else {
332  converted_decimal_value = (converted_decimal_value - 5) / 10;
333  }
334  }
335  }
336  return converted_decimal_value;
337 }
HOST DEVICE int get_scale() const
Definition: sqltypes.h:316

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

bool DatumEqual ( const Datum  a,
const Datum  b,
const SQLTypeInfo ti 
)

Definition at line 190 of file Datum.cpp.

References Datum::bigintval, Datum::boolval, Datum::doubleval, Datum::floatval, SQLTypeInfo::get_compression(), SQLTypeInfo::get_type(), Datum::intval, kBIGINT, kBOOLEAN, kCHAR, kDATE, kDECIMAL, kDOUBLE, kENCODING_DICT, kFLOAT, kINT, kINTERVAL_DAY_TIME, kINTERVAL_YEAR_MONTH, kLINESTRING, kMULTIPOLYGON, kNUMERIC, kPOINT, kPOLYGON, kSMALLINT, kTEXT, kTIME, kTIMESTAMP, kTINYINT, kVARCHAR, Datum::smallintval, Datum::stringval, and Datum::tinyintval.

Referenced by ChunkMetadata::operator==(), FixedLengthArrayNoneEncoder::resetChunkStats(), and ArrayNoneEncoder::resetChunkStats().

190  {
191  switch (ti.get_type()) {
192  case kBOOLEAN:
193  return a.boolval == b.boolval;
194  case kBIGINT:
195  case kNUMERIC:
196  case kDECIMAL:
197  return a.bigintval == b.bigintval;
198  case kINT:
199  return a.intval == b.intval;
200  case kSMALLINT:
201  return a.smallintval == b.smallintval;
202  case kTINYINT:
203  return a.tinyintval == b.tinyintval;
204  case kFLOAT:
205  return a.floatval == b.floatval;
206  case kDOUBLE:
207  return a.doubleval == b.doubleval;
208  case kTIME:
209  case kTIMESTAMP:
210  case kDATE:
211  case kINTERVAL_DAY_TIME:
213  return a.bigintval == b.bigintval;
214  case kTEXT:
215  case kVARCHAR:
216  case kCHAR:
217  case kPOINT:
218  case kLINESTRING:
219  case kPOLYGON:
220  case kMULTIPOLYGON:
221  if (ti.get_compression() == kENCODING_DICT) {
222  return a.intval == b.intval;
223  }
224  if (a.stringval == nullptr && b.stringval == nullptr) {
225  return true;
226  }
227  if (a.stringval == nullptr || b.stringval == nullptr) {
228  return false;
229  }
230  return *a.stringval == *b.stringval;
231  default:
232  return false;
233  }
234  return false;
235 }
int8_t tinyintval
Definition: sqltypes.h:203
Definition: sqltypes.h:48
bool boolval
Definition: sqltypes.h:202
HOST DEVICE SQLTypes get_type() const
Definition: sqltypes.h:311
int32_t intval
Definition: sqltypes.h:205
float floatval
Definition: sqltypes.h:207
int64_t bigintval
Definition: sqltypes.h:206
int16_t smallintval
Definition: sqltypes.h:204
std::string * stringval
Definition: sqltypes.h:211
Definition: sqltypes.h:51
Definition: sqltypes.h:52
HOST DEVICE EncodingType get_compression() const
Definition: sqltypes.h:319
Definition: sqltypes.h:40
Definition: sqltypes.h:44
double doubleval
Definition: sqltypes.h:208

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

std::string DatumToString ( Datum  d,
const SQLTypeInfo ti 
)

Definition at line 240 of file Datum.cpp.

References Datum::bigintval, Datum::boolval, CHECK_EQ, CHECK_LE, CHECK_LT, Datum::doubleval, Datum::floatval, shared::formatDate(), shared::formatDateTime(), shared::formatHMS(), SQLTypeInfo::get_dimension(), SQLTypeInfo::get_scale(), SQLTypeInfo::get_type(), SQLTypeInfo::get_type_name(), Datum::intval, kBIGINT, kBOOLEAN, kCHAR, kDATE, kDECIMAL, kDOUBLE, kFLOAT, kINT, kINTERVAL_DAY_TIME, kINTERVAL_YEAR_MONTH, kNUMERIC, kSMALLINT, kTEXT, kTIME, kTIMESTAMP, kTINYINT, kVARCHAR, Datum::smallintval, Datum::stringval, Datum::tinyintval, to_string(), and SQLTypeInfo::to_string().

Referenced by Analyzer::Constant::cast_to_string(), foreign_storage::datetime_to_string(), datum_to_string(), ChunkMetadata::dump(), anonymous_namespace{ArrowImporter.h}::ArrowValue< int64_t >::operator const std::string(), Analyzer::Constant::toString(), Fragmenter_Namespace::InsertOrderFragmenter::updateChunkStats(), and ScalarExprToSql::visitConstant().

240  {
241  constexpr size_t buf_size = 64;
242  char buf[buf_size]; // Hold "2000-03-01 12:34:56.123456789" and large years.
243  switch (ti.get_type()) {
244  case kBOOLEAN:
245  if (d.boolval) {
246  return "t";
247  }
248  return "f";
249  case kNUMERIC:
250  case kDECIMAL: {
251  double v = (double)d.bigintval / pow(10, ti.get_scale());
252  int size = snprintf(buf, buf_size, "%*.*f", ti.get_dimension(), ti.get_scale(), v);
253  CHECK_LE(0, size) << v << ' ' << ti.to_string();
254  CHECK_LT(size_t(size), buf_size) << v << ' ' << ti.to_string();
255  return buf;
256  }
257  case kINT:
258  return std::to_string(d.intval);
259  case kSMALLINT:
260  return std::to_string(d.smallintval);
261  case kTINYINT:
262  return std::to_string(d.tinyintval);
263  case kBIGINT:
264  return std::to_string(d.bigintval);
265  case kFLOAT:
266  return std::to_string(d.floatval);
267  case kDOUBLE:
268  return std::to_string(d.doubleval);
269  case kTIME: {
270  size_t const len = shared::formatHMS(buf, buf_size, d.bigintval);
271  CHECK_EQ(8u, len); // 8 == strlen("HH:MM:SS")
272  return buf;
273  }
274  case kTIMESTAMP: {
275  unsigned const dim = ti.get_dimension(); // assumes dim <= 9
276  size_t const len = shared::formatDateTime(buf, buf_size, d.bigintval, dim);
277  CHECK_LE(19u + bool(dim) + dim, len); // 19 = strlen("YYYY-MM-DD HH:MM:SS")
278  return buf;
279  }
280  case kDATE: {
281  size_t const len = shared::formatDate(buf, buf_size, d.bigintval);
282  CHECK_LE(10u, len); // 10 == strlen("YYYY-MM-DD")
283  return buf;
284  }
285  case kINTERVAL_DAY_TIME:
286  return std::to_string(d.bigintval) + " ms (day-time interval)";
288  return std::to_string(d.bigintval) + " month(s) (year-month interval)";
289  case kTEXT:
290  case kVARCHAR:
291  case kCHAR:
292  if (d.stringval == nullptr) {
293  return "NULL";
294  }
295  return *d.stringval;
296  default:
297  throw std::runtime_error("Internal error: invalid type " + ti.get_type_name() +
298  " in DatumToString.");
299  }
300  return "";
301 }
int8_t tinyintval
Definition: sqltypes.h:203
#define CHECK_EQ(x, y)
Definition: Logger.h:205
Definition: sqltypes.h:48
bool boolval
Definition: sqltypes.h:202
HOST DEVICE int get_scale() const
Definition: sqltypes.h:316
size_t formatDateTime(char *buf, size_t const max, int64_t const timestamp, int const dimension)
Definition: misc.cpp:43
HOST DEVICE SQLTypes get_type() const
Definition: sqltypes.h:311
int32_t intval
Definition: sqltypes.h:205
std::string to_string(char const *&&v)
size_t formatHMS(char *buf, size_t const max, int64_t const unixtime)
Definition: misc.cpp:80
float floatval
Definition: sqltypes.h:207
std::string to_string() const
Definition: sqltypes.h:446
int64_t bigintval
Definition: sqltypes.h:206
int16_t smallintval
Definition: sqltypes.h:204
std::string * stringval
Definition: sqltypes.h:211
size_t formatDate(char *buf, size_t const max, int64_t const unixtime)
Definition: misc.cpp:25
#define CHECK_LT(x, y)
Definition: Logger.h:207
Definition: sqltypes.h:51
Definition: sqltypes.h:52
#define CHECK_LE(x, y)
Definition: Logger.h:208
HOST DEVICE int get_dimension() const
Definition: sqltypes.h:313
std::string get_type_name() const
Definition: sqltypes.h:414
Definition: sqltypes.h:40
Definition: sqltypes.h:44
double doubleval
Definition: sqltypes.h:208

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

SQLTypes decimal_to_int_type ( const SQLTypeInfo ti)

Definition at line 303 of file Datum.cpp.

References CHECK, SQLTypeInfo::get_size(), kBIGINT, kINT, kNULLT, kSMALLINT, and kTINYINT.

Referenced by import_export::TypedImportBuffer::add_value(), CodeGenerator::codegen(), CodeGenerator::codegenIntConst(), anonymous_namespace{LogicalIR.cpp}::contains_unsafe_division(), import_export::Loader::distributeToShards(), extract_from_datum(), anonymous_namespace{ColumnIR.cpp}::get_col_decoder(), CgenState::getOrAddLiteral(), ResultSet::makeTargetValue(), import_export::NullArrayDatum(), import_export::NullDatum(), import_export::TypedImportBuffer::pop_value(), import_export::TDatumToDatum(), anonymous_namespace{ExpressionRewrite.cpp}::ConstantFoldingVisitor::visitBinOper(), and anonymous_namespace{ExpressionRewrite.cpp}::ConstantFoldingVisitor::visitUOper().

303  {
304  switch (ti.get_size()) {
305  case 1:
306  return kTINYINT;
307  case 2:
308  return kSMALLINT;
309  case 4:
310  return kINT;
311  case 8:
312  return kBIGINT;
313  default:
314  CHECK(false);
315  }
316  return kNULLT;
317 }
HOST DEVICE int get_size() const
Definition: sqltypes.h:321
#define CHECK(condition)
Definition: Logger.h:197
Definition: sqltypes.h:44

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int64_t parse_numeric ( const std::string_view  s,
SQLTypeInfo ti 
)

Definition at line 71 of file Datum.cpp.

References CHECK_GE, SQLTypeInfo::get_dimension(), SQLTypeInfo::get_scale(), generate_TableFunctionsFactory_init::i, run_benchmark_import::result, SQLTypeInfo::set_dimension(), SQLTypeInfo::set_notnull(), SQLTypeInfo::set_scale(), and to_string().

Referenced by StringToDatum().

71  {
72  assert(s.length() <= 20);
73  size_t dot = s.find_first_of('.', 0);
74  std::string before_dot;
75  std::string after_dot;
76  if (dot != std::string::npos) {
77  // make .99 as 0.99, or std::stoll below throws exception 'std::invalid_argument'
78  before_dot = (0 == dot) ? "0" : s.substr(0, dot);
79  after_dot = s.substr(dot + 1);
80  } else {
81  before_dot = s;
82  after_dot = "0";
83  }
84  const bool is_negative = before_dot.find_first_of('-', 0) != std::string::npos;
85  const int64_t sign = is_negative ? -1 : 1;
86  int64_t result;
87  result = std::abs(std::stoll(before_dot));
88  int64_t fraction = 0;
89  const size_t before_dot_digits = before_dot.length() - (is_negative ? 1 : 0);
90  if (!after_dot.empty()) {
91  fraction = std::stoll(after_dot);
92  }
93  if (ti.get_dimension() == 0) {
94  // set the type info based on the literal string
95  ti.set_scale(static_cast<int>(after_dot.length()));
96  ti.set_dimension(static_cast<int>(before_dot_digits + ti.get_scale()));
97  ti.set_notnull(false);
98  } else {
99  CHECK_GE(ti.get_scale(), 0);
100  if (before_dot_digits + ti.get_scale() > static_cast<size_t>(ti.get_dimension())) {
101  throw std::runtime_error("numeric value " + std::string(s) +
102  " exceeds the maximum precision of " +
104  }
105  for (size_t i = static_cast<size_t>(ti.get_scale()); i < after_dot.length(); ++i) {
106  fraction /= 10; // truncate the digits after decimal point.
107  }
108  }
109  // the following loop can be made more efficient if needed
110  for (int i = 0; i < ti.get_scale(); i++) {
111  result *= 10;
112  }
113  if (result < 0) {
114  result -= fraction;
115  } else {
116  result += fraction;
117  }
118  return result * sign;
119 }
HOST DEVICE int get_scale() const
Definition: sqltypes.h:316
#define CHECK_GE(x, y)
Definition: Logger.h:210
std::string to_string(char const *&&v)
void set_scale(int s)
Definition: sqltypes.h:406
void set_dimension(int d)
Definition: sqltypes.h:403
HOST DEVICE int get_dimension() const
Definition: sqltypes.h:313
void set_notnull(bool n)
Definition: sqltypes.h:408

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

Datum StringToDatum ( std::string_view  s,
SQLTypeInfo ti 
)

Definition at line 124 of file Datum.cpp.

References Datum::bigintval, Datum::boolval, Datum::doubleval, Datum::floatval, SQLTypeInfo::get_dimension(), SQLTypeInfo::get_type(), SQLTypeInfo::get_type_name(), Datum::intval, kARRAY, kBIGINT, kBOOLEAN, kCOLUMN, kDATE, kDECIMAL, kDOUBLE, kFLOAT, kINT, kLINESTRING, kMULTIPOLYGON, kNUMERIC, kPOINT, kPOLYGON, kSMALLINT, kTIME, kTIMESTAMP, kTINYINT, parse_numeric(), Datum::smallintval, Datum::tinyintval, and to_upper().

Referenced by import_export::TypedImportBuffer::add_value(), Parser::FixedPtLiteral::analyze(), Analyzer::Constant::cast_from_string(), anonymous_namespace{ArrowImporter.h}::ArrowValue< std::string >::operator const bool(), anonymous_namespace{ArrowImporter.h}::ArrowValue< std::string >::operator const DATA_TYPE(), populate_TColumn(), and import_export::StringToArray().

124  {
125  Datum d;
126  try {
127  switch (ti.get_type()) {
128  case kARRAY:
129  case kCOLUMN:
130  break;
131  case kBOOLEAN:
132  if (s == "t" || s == "T" || s == "1" || to_upper(std::string(s)) == "TRUE") {
133  d.boolval = true;
134  } else if (s == "f" || s == "F" || s == "0" ||
135  to_upper(std::string(s)) == "FALSE") {
136  d.boolval = false;
137  } else {
138  throw std::runtime_error("Invalid string for boolean " + std::string(s));
139  }
140  break;
141  case kNUMERIC:
142  case kDECIMAL:
143  d.bigintval = parse_numeric(s, ti);
144  break;
145  case kBIGINT:
146  d.bigintval = std::stoll(std::string(s));
147  break;
148  case kINT:
149  d.intval = std::stoi(std::string(s));
150  break;
151  case kSMALLINT:
152  d.smallintval = std::stoi(std::string(s));
153  break;
154  case kTINYINT:
155  d.tinyintval = std::stoi(std::string(s));
156  break;
157  case kFLOAT:
158  d.floatval = std::stof(std::string(s));
159  break;
160  case kDOUBLE:
161  d.doubleval = std::stod(std::string(s));
162  break;
163  case kTIME:
164  d.bigintval = dateTimeParse<kTIME>(s, ti.get_dimension());
165  break;
166  case kTIMESTAMP:
167  d.bigintval = dateTimeParse<kTIMESTAMP>(s, ti.get_dimension());
168  break;
169  case kDATE:
170  d.bigintval = dateTimeParse<kDATE>(s, ti.get_dimension());
171  break;
172  case kPOINT:
173  case kLINESTRING:
174  case kPOLYGON:
175  case kMULTIPOLYGON:
176  throw std::runtime_error("Internal error: geometry type in StringToDatum.");
177  default:
178  throw std::runtime_error("Internal error: invalid type in StringToDatum: " +
179  ti.get_type_name());
180  }
181  } catch (const std::invalid_argument&) {
182  throw std::runtime_error("Invalid conversion from string to " + ti.get_type_name());
183  } catch (const std::out_of_range&) {
184  throw std::runtime_error("Got out of range error during conversion from string to " +
185  ti.get_type_name());
186  }
187  return d;
188 }
int8_t tinyintval
Definition: sqltypes.h:203
Definition: sqltypes.h:48
int64_t parse_numeric(const std::string_view s, SQLTypeInfo &ti)
Definition: Datum.cpp:71
bool boolval
Definition: sqltypes.h:202
HOST DEVICE SQLTypes get_type() const
Definition: sqltypes.h:311
int32_t intval
Definition: sqltypes.h:205
float floatval
Definition: sqltypes.h:207
int64_t bigintval
Definition: sqltypes.h:206
int16_t smallintval
Definition: sqltypes.h:204
std::string to_upper(const std::string &str)
Definition: sqltypes.h:52
HOST DEVICE int get_dimension() const
Definition: sqltypes.h:313
std::string get_type_name() const
Definition: sqltypes.h:414
Definition: sqltypes.h:44
double doubleval
Definition: sqltypes.h:208

+ Here is the call graph for this function:

+ Here is the caller graph for this function: