http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/binary_operations/MultiplyBinaryOperation.cpp ---------------------------------------------------------------------- diff --git a/types/operations/binary_operations/MultiplyBinaryOperation.cpp b/types/operations/binary_operations/MultiplyBinaryOperation.cpp deleted file mode 100644 index a206364..0000000 --- a/types/operations/binary_operations/MultiplyBinaryOperation.cpp +++ /dev/null @@ -1,410 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - **/ - -#include "types/operations/binary_operations/MultiplyBinaryOperation.hpp" - -#include <string> -#include <utility> - -#include "types/DateOperatorOverloads.hpp" -#include "types/DatetimeIntervalType.hpp" -#include "types/DoubleType.hpp" -#include "types/FloatType.hpp" -#include "types/IntType.hpp" -#include "types/IntervalLit.hpp" -#include "types/LongType.hpp" -#include "types/Type.hpp" -#include "types/TypeErrors.hpp" -#include "types/TypeFactory.hpp" -#include "types/TypeID.hpp" -#include "types/YearMonthIntervalType.hpp" -#include "types/operations/binary_operations/ArithmeticBinaryOperators.hpp" -#include "utility/EqualsAnyConstant.hpp" - -#include "glog/logging.h" - -namespace quickstep { - -bool MultiplyBinaryOperation::canApplyToTypes(const Type &left, const Type &right) const { - switch (left.getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: { - return (right.getSuperTypeID() == Type::kNumeric || - right.getTypeID() == kDatetimeInterval || - right.getTypeID() == kYearMonthInterval); - } - case kDatetimeInterval: - case kYearMonthInterval: { - return (right.getSuperTypeID() == Type::kNumeric); - } - default: - return false; - } -} - -const Type* MultiplyBinaryOperation::resultTypeForArgumentTypes(const Type &left, const Type &right) const { - if (left.getSuperTypeID() == Type::kNumeric && right.getSuperTypeID() == Type::kNumeric) { - return TypeFactory::GetUnifyingType(left, right); - } else if ((left.getSuperTypeID() == Type::kNumeric && right.getTypeID() == kDatetimeInterval) || - (left.getTypeID() == kDatetimeInterval && right.getSuperTypeID() == Type::kNumeric)) { - return &(DatetimeIntervalType::Instance(left.isNullable() || right.isNullable())); - } else if ((left.getSuperTypeID() == Type::kNumeric && right.getTypeID() == kYearMonthInterval) || - (left.getTypeID() == kYearMonthInterval && right.getSuperTypeID() == Type::kNumeric)) { - return &(YearMonthIntervalType::Instance(left.isNullable() || right.isNullable())); - } else { - return nullptr; - } -} - -const Type* MultiplyBinaryOperation::resultTypeForPartialArgumentTypes( - const Type *left, - const Type *right) const { - if ((left == nullptr) && (right == nullptr)) { - return nullptr; - } - - if ((left != nullptr) && (right != nullptr)) { - return resultTypeForArgumentTypes(*left, *right); - } - - // Multiplication is commutative, so we just determine based on the known - // type, left or right. - const Type *known_type = (left != nullptr) ? left : right; - switch (known_type->getTypeID()) { - case kDatetimeInterval: - // DatetimeInterval can be multiplied against any numeric type, yielding - // DatetimeInterval. - return &TypeFactory::GetType(kDatetimeInterval, true); - case kYearMonthInterval: - // Same deal for YearMonthInterval. - return &TypeFactory::GetType(kYearMonthInterval, true); - default: - // Ambiguous or inapplicable. Note that we can't apply numeric precedence - // order for a Double argument, because the other argument could be a - // numeric type OR an interval type. - return nullptr; - } -} - -bool MultiplyBinaryOperation::partialTypeSignatureIsPlausible( - const Type *result_type, - const Type *left_argument_type, - const Type *right_argument_type) const { - if ((left_argument_type == nullptr) && (right_argument_type == nullptr)) { - if (result_type == nullptr) { - return true; - } else if (!result_type->isNullable()) { - // Unknown arguments are assumed to be nullable, since they arise from - // untyped NULL literals in the parser. Therefore, a non-nullable result - // Type is not plausible with unknown arguments. - return false; - } else { - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kInt, kLong, kFloat, kDouble, kDatetimeInterval, kYearMonthInterval); - } - } - - if ((left_argument_type != nullptr) && (right_argument_type != nullptr)) { - const Type *actual_result_type = resultTypeForArgumentTypes(*left_argument_type, - *right_argument_type); - if (actual_result_type == nullptr) { - // Both argument Types are known, but this operation is NOT applicable to - // them. No matter what the result_type is, the signature is not - // plausible. - return false; - } else if (result_type == nullptr) { - return true; - } else { - return result_type->equals(*actual_result_type); - } - } - - // Multiplication is commutative, so we just determine based on the known - // type, left or right. - const Type *known_argument_type = (left_argument_type != nullptr) - ? left_argument_type - : right_argument_type; - if (result_type == nullptr) { - return QUICKSTEP_EQUALS_ANY_CONSTANT( - known_argument_type->getTypeID(), - kInt, kLong, kFloat, kDouble, kDatetimeInterval, kYearMonthInterval); - } - - if (!result_type->isNullable()) { - // One of the arguments is unknown, but it is nevertheless assumed - // nullable, since unknown argument Types arise from untyped NULL literals - // in the parser. Therefore, a non-nullable result Type is not plausible - // with an unknown argument. - return false; - } - - switch (result_type->getTypeID()) { - case kInt: - return (known_argument_type->getTypeID() == kInt); - case kLong: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - known_argument_type->getTypeID(), - kInt, kLong); - case kFloat: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - known_argument_type->getTypeID(), - kInt, kFloat); - case kDouble: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - known_argument_type->getTypeID(), - kInt, kLong, kFloat, kDouble); - case kDatetimeInterval: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - known_argument_type->getTypeID(), - kInt, kLong, kFloat, kDouble, kDatetimeInterval); - case kYearMonthInterval: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - known_argument_type->getTypeID(), - kInt, kLong, kFloat, kDouble, kYearMonthInterval); - default: - return false; - } -} - -std::pair<const Type*, const Type*> MultiplyBinaryOperation::pushDownTypeHint( - const Type *result_type_hint) const { - if (result_type_hint == nullptr) { - return std::pair<const Type*, const Type*>(nullptr, nullptr); - } - - switch (result_type_hint->getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: - return std::pair<const Type*, const Type*>(result_type_hint, result_type_hint); - case kDatetimeInterval: - case kYearMonthInterval: - // Ambiguous hint. One of the arguments should be the same as the - // '*type_hint', the other can be any numeric type, but either order is - // OK. - return std::pair<const Type*, const Type*>(nullptr, nullptr); - default: - // Inapplicable. - return std::pair<const Type*, const Type*>(nullptr, nullptr); - } -} - -TypedValue MultiplyBinaryOperation::applyToChecked(const TypedValue &left, - const Type &left_type, - const TypedValue &right, - const Type &right_type) const { - switch (left_type.getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: { - if (right_type.getSuperTypeID() == Type::kNumeric) { - return applyToCheckedNumericHelper<MultiplyFunctor>(left, left_type, - right, right_type); - } else if (right_type.getTypeID() == kDatetimeInterval) { - return applyToCheckedIntervalMultiplyNumericHelper<DatetimeIntervalType>(right, right_type, - left, left_type); - } else if (right_type.getTypeID() == kYearMonthInterval) { - return applyToCheckedIntervalMultiplyNumericHelper<YearMonthIntervalType>(right, right_type, - left, left_type); - } - break; - } - case kDatetimeInterval: { - if (right_type.getSuperTypeID() == Type::kNumeric) { - return applyToCheckedIntervalMultiplyNumericHelper<DatetimeIntervalType>(left, left_type, - right, right_type); - } - break; - } - case kYearMonthInterval: { - if (right_type.getSuperTypeID() == Type::kNumeric) { - return applyToCheckedIntervalMultiplyNumericHelper<YearMonthIntervalType>(left, left_type, - right, right_type); - } - break; - } - default: - break; - } - - LOG(FATAL) << "Can not apply " << getName() << " to arguments of types " - << left_type.getName() << " and " << right_type.getName(); -} - -UncheckedBinaryOperator* MultiplyBinaryOperation::makeUncheckedBinaryOperatorForTypes(const Type &left, - const Type &right) const { - switch (left.getTypeID()) { - case kInt: { - if (right.getSuperTypeID() == Type::kNumeric) { - return makeNumericBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator>(left, right); - } else if (right.getTypeID() == kDatetimeInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - IntType::cpptype, DatetimeIntervalLit>(left, right); - } else if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - IntType::cpptype, YearMonthIntervalLit>(left, right); - } - break; - } - case kLong: { - if (right.getSuperTypeID() == Type::kNumeric) { - return makeNumericBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator>(left, right); - } else if (right.getTypeID() == kDatetimeInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - LongType::cpptype, DatetimeIntervalLit>(left, right); - } else if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - LongType::cpptype, YearMonthIntervalLit>(left, right); - } - break; - } - case kFloat: { - if (right.getSuperTypeID() == Type::kNumeric) { - return makeNumericBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator>(left, right); - } else if (right.getTypeID() == kDatetimeInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - FloatType::cpptype, DatetimeIntervalLit>(left, right); - } else if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - FloatType::cpptype, YearMonthIntervalLit>(left, right); - } - break; - } - case kDouble: { - if (right.getSuperTypeID() == Type::kNumeric) { - return makeNumericBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator>(left, right); - } else if (right.getTypeID() == kDatetimeInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DoubleType::cpptype, DatetimeIntervalLit>(left, right); - } else if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - DoubleType::cpptype, YearMonthIntervalLit>(left, right); - } - break; - } - case kDatetimeInterval: { - switch (right.getTypeID()) { - case kInt: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DatetimeIntervalLit, IntType::cpptype>(left, right); - } - case kLong: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DatetimeIntervalLit, LongType::cpptype>(left, right); - } - case kFloat: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DatetimeIntervalLit, FloatType::cpptype>(left, right); - } - case kDouble: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DatetimeIntervalLit, DoubleType::cpptype>(left, right); - } - default: - break; - } - break; - } - case kYearMonthInterval: { - switch (right.getTypeID()) { - case kInt: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - YearMonthIntervalLit, IntType::cpptype>(left, right); - } - case kLong: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - YearMonthIntervalLit, LongType::cpptype>(left, right); - } - case kFloat: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - YearMonthIntervalLit, FloatType::cpptype>(left, right); - } - case kDouble: { - return makeDateBinaryOperatorOuterHelper<MultiplyArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - YearMonthIntervalLit, DoubleType::cpptype>(left, right); - } - default: - break; - } - break; - } - default: - break; - } - - throw OperationInapplicableToType(getName(), 2, left.getName().c_str(), right.getName().c_str()); -} - -template <typename IntervalType> -TypedValue MultiplyBinaryOperation::applyToCheckedIntervalMultiplyNumericHelper( - const TypedValue &left, - const Type &left_type, - const TypedValue &right, - const Type &right_type) const { - DCHECK(IntervalType::kStaticTypeID == kDatetimeInterval || - IntervalType::kStaticTypeID == kYearMonthInterval); - DCHECK(IntervalType::kStaticTypeID == left_type.getTypeID()); - DCHECK_EQ(Type::kNumeric, right_type.getSuperTypeID()); - - if (left.isNull() || right.isNull()) { - return TypedValue(IntervalType::kStaticTypeID); - } - - switch (right_type.getTypeID()) { - case kInt: { - return TypedValue(left.getLiteral<typename IntervalType::cpptype>() * right.getLiteral<IntType::cpptype>()); - } - case kLong: { - return TypedValue(left.getLiteral<typename IntervalType::cpptype>() * right.getLiteral<LongType::cpptype>()); - } - case kFloat: { - return TypedValue(left.getLiteral<typename IntervalType::cpptype>() * right.getLiteral<FloatType::cpptype>()); - } - case kDouble: { - return TypedValue(left.getLiteral<typename IntervalType::cpptype>() * right.getLiteral<DoubleType::cpptype>()); - } - default: { - LOG(FATAL) << "Can not apply " << getName() << " to arguments of types " - << left_type.getName() << " and " << right_type.getName(); - } - } -} - -} // namespace quickstep
http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/binary_operations/MultiplyBinaryOperation.hpp ---------------------------------------------------------------------- diff --git a/types/operations/binary_operations/MultiplyBinaryOperation.hpp b/types/operations/binary_operations/MultiplyBinaryOperation.hpp deleted file mode 100644 index 6edc999..0000000 --- a/types/operations/binary_operations/MultiplyBinaryOperation.hpp +++ /dev/null @@ -1,98 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - **/ - -#ifndef QUICKSTEP_TYPES_OPERATIONS_BINARY_OPERATIONS_MULTIPLY_BINARY_OPERATION_HPP_ -#define QUICKSTEP_TYPES_OPERATIONS_BINARY_OPERATIONS_MULTIPLY_BINARY_OPERATION_HPP_ - -#include <utility> - -#include "types/TypedValue.hpp" -#include "types/operations/binary_operations/ArithmeticBinaryOperation.hpp" -#include "types/operations/binary_operations/BinaryOperationID.hpp" -#include "utility/Macros.hpp" - -namespace quickstep { - -class Type; -class UncheckedBinaryOperator; - -/** \addtogroup Types - * @{ - */ - -/** - * @brief The BinaryOperation for multiplication. - **/ -class MultiplyBinaryOperation : public ArithmeticBinaryOperation { - public: - /** - * @brief Get a reference to the singleton instance of this Operation. - * - * @return A reference to the singleton instance of this Operation. - **/ - static const MultiplyBinaryOperation& Instance() { - static MultiplyBinaryOperation instance; - return instance; - } - - bool canApplyToTypes(const Type &left, - const Type &right) const override; - - const Type* resultTypeForArgumentTypes(const Type &left, - const Type &right) const override; - - const Type* resultTypeForPartialArgumentTypes(const Type *left, - const Type *right) const override; - - bool partialTypeSignatureIsPlausible(const Type *result_type, - const Type *left_argument_type, - const Type *right_argument_type) const override; - - std::pair<const Type*, const Type*> pushDownTypeHint( - const Type *result_type_hint) const override; - - TypedValue applyToChecked(const TypedValue &left, - const Type &left_type, - const TypedValue &right, - const Type &right_type) const override; - - UncheckedBinaryOperator* makeUncheckedBinaryOperatorForTypes(const Type &left, - const Type &right) const override; - - private: - MultiplyBinaryOperation() - : ArithmeticBinaryOperation(BinaryOperationID::kMultiply) { - } - - // NOTE(zuyu): left is an Interval TypedValue, either DatetimeInterval - // or YearMonthInterval, while right is a Numeric. - template <typename IntervalType> - TypedValue applyToCheckedIntervalMultiplyNumericHelper(const TypedValue &left, - const Type &left_type, - const TypedValue &right, - const Type &right_type) const; - - DISALLOW_COPY_AND_ASSIGN(MultiplyBinaryOperation); -}; - -/** @} */ - -} // namespace quickstep - -#endif // QUICKSTEP_TYPES_OPERATIONS_BINARY_OPERATIONS_MULTIPLY_BINARY_OPERATION_HPP_ http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/binary_operations/SubtractBinaryOperation.cpp ---------------------------------------------------------------------- diff --git a/types/operations/binary_operations/SubtractBinaryOperation.cpp b/types/operations/binary_operations/SubtractBinaryOperation.cpp deleted file mode 100644 index 53e4266..0000000 --- a/types/operations/binary_operations/SubtractBinaryOperation.cpp +++ /dev/null @@ -1,459 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - **/ - -#include "types/operations/binary_operations/SubtractBinaryOperation.hpp" - -#include <string> -#include <utility> - -#include "types/DateOperatorOverloads.hpp" -#include "types/DateType.hpp" -#include "types/DatetimeIntervalType.hpp" -#include "types/DatetimeLit.hpp" -#include "types/DatetimeType.hpp" -#include "types/IntervalLit.hpp" -#include "types/Type.hpp" -#include "types/TypeErrors.hpp" -#include "types/TypeFactory.hpp" -#include "types/TypeID.hpp" -#include "types/YearMonthIntervalType.hpp" -#include "types/operations/binary_operations/ArithmeticBinaryOperators.hpp" -#include "utility/EqualsAnyConstant.hpp" - -#include "glog/logging.h" - -namespace quickstep { - -bool SubtractBinaryOperation::canApplyToTypes(const Type &left, const Type &right) const { - switch (left.getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: { - return (right.getSuperTypeID() == Type::kNumeric); - } - case kDate: { - return (right.getTypeID() == kYearMonthInterval); - } - case kDatetime: { - return (right.getTypeID() == kDatetime || - right.getTypeID() == kDatetimeInterval || - right.getTypeID() == kYearMonthInterval); - } - case kDatetimeInterval: { - return (right.getTypeID() == kDatetimeInterval); - } - case kYearMonthInterval: { - return (right.getTypeID() == kYearMonthInterval || - right.getTypeID() == kDate); - } - default: - return false; - } -} - -const Type* SubtractBinaryOperation::resultTypeForArgumentTypes(const Type &left, const Type &right) const { - if (left.getSuperTypeID() == Type::kNumeric && right.getSuperTypeID() == Type::kNumeric) { - return TypeFactory::GetUnifyingType(left, right); - } else if ((left.getTypeID() == kDate && right.getTypeID() == kYearMonthInterval)) { - // For DATE type, only one possibility: DATE - YEAR-MONTH-INTERVAL. - return &(DateType::Instance(left.isNullable() || right.isNullable())); - } else if ((left.getTypeID() == kDatetime && right.getTypeID() == kDatetime) || - (left.getTypeID() == kDatetimeInterval && right.getTypeID() == kDatetimeInterval)) { - // NOTE(zuyu): we set the result type of the Subtract - // between two Datetimes as DatetimeInterval, instead of YearMonthInterval. - return &(DatetimeIntervalType::Instance(left.isNullable() || right.isNullable())); - } else if (left.getTypeID() == kDatetime && right.getTypeID() == kDatetimeInterval) { - return &(DatetimeType::Instance(left.isNullable() || right.isNullable())); - } else if (left.getTypeID() == kDatetime && right.getTypeID() == kYearMonthInterval) { - return &(DatetimeType::Instance(left.isNullable() || right.isNullable())); - } else if (left.getTypeID() == kYearMonthInterval && right.getTypeID() == kYearMonthInterval) { - return &(YearMonthIntervalType::Instance(left.isNullable() || right.isNullable())); - } else { - return nullptr; - } -} - -const Type* SubtractBinaryOperation::resultTypeForPartialArgumentTypes( - const Type *left, - const Type *right) const { - if (left == nullptr) { - if (right == nullptr) { - return nullptr; - } else { - switch (right->getTypeID()) { - case kDouble: - // Double has highest precedence of numeric types. - return &TypeFactory::GetType(kDouble, true); - case kDatetime: - // If the subtrahend is Datetime, then the only allowed minuend is - // another Datetime, and the result is an interval. - return &TypeFactory::GetType(kDatetimeInterval, true); - default: - // Ambiguous or inapplicable. - return nullptr; - } - } - } else { - if (right == nullptr) { - switch (left->getTypeID()) { - case kDouble: - // Double has highest precedence of numeric types. - return &TypeFactory::GetType(kDouble, true); - case kDate: - // If left is a Date, right must be a YearMonthInterval and the result - // must be a Date. - return &TypeFactory::GetType(kDate, true); - case kDatetimeInterval: - // If minuend is a DatetimeInterval, the subtrahend and result must - // also be DatetimeInterval. - return &TypeFactory::GetType(kDatetimeInterval, true); - case kYearMonthInterval: - // Similarly, if minuend is a YearMonthInterval, the subtrahend and - // result must also be YearMonthInterval. - return &TypeFactory::GetType(kYearMonthInterval, true); - default: - // Ambiguous or inapplicable. - return nullptr; - } - } else { - return resultTypeForArgumentTypes(*left, *right); - } - } -} - -bool SubtractBinaryOperation::partialTypeSignatureIsPlausible( - const Type *result_type, - const Type *left_argument_type, - const Type *right_argument_type) const { - // Early check: if either argument type is nullable or unknown, result type - // must also be nullable. - if ((left_argument_type == nullptr) - || left_argument_type->isNullable() - || (right_argument_type == nullptr) - || right_argument_type->isNullable()) { - if ((result_type != nullptr) && (!result_type->isNullable())) { - return false; - } - } - - if (left_argument_type == nullptr) { - if (right_argument_type == nullptr) { - if (result_type == nullptr) { - // All types unknown. - return true; - } else { - // Only result type is known, just check that it is one of the types - // that can possibly be returned. - return QUICKSTEP_EQUALS_ANY_CONSTANT(result_type->getTypeID(), - kInt, - kLong, - kFloat, - kDouble, - kDate, - kDatetime, - kDatetimeInterval, - kYearMonthInterval); - } - } - - if (result_type == nullptr) { - // Right (minuend) argument type is known, left (subtrahend) argument and - // result types are unknown. Just check that right (minuend) type can be - // subtracted. - return QUICKSTEP_EQUALS_ANY_CONSTANT(right_argument_type->getTypeID(), - kInt, - kLong, - kFloat, - kDouble, - kDatetime, - kDatetimeInterval, - kYearMonthInterval); - } - - // Return type and right (minuend) argument type are known, left - // (subtrahend) argument type is unknown. Check that result and subtrahend - // are compatible. - switch (right_argument_type->getTypeID()) { - case kInt: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kInt, kLong, kFloat, kDouble); - case kLong: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kLong, kDouble); - case kFloat: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kFloat, kDouble); - case kDouble: - return (result_type->getTypeID() == kDouble); - case kDate: - return (result_type->getTypeID() == kDate); - case kDatetime: - return (result_type->getTypeID() == kDatetimeInterval); - case kDatetimeInterval: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kDatetime, kDatetimeInterval); - case kYearMonthInterval: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kDate, kDatetime, kYearMonthInterval); - default: - return false; - } - } else { // left_argument_type != nullptr - if (right_argument_type == nullptr) { - if (result_type == nullptr) { - // Left (subtrahend) argument type is known, right (minuend) argument - // type and result type are unknown. Just check that the left - // (subtrahend) type can be subtracted from. - return QUICKSTEP_EQUALS_ANY_CONSTANT(left_argument_type->getTypeID(), - kInt, - kLong, - kFloat, - kDouble, - kDate, - kDatetime, - kDatetimeInterval, - kYearMonthInterval); - } - - // Result type and left (subtrahend) argument type are known, but right - // (minuend) argument type is unknown. Check that result and minuend are - // compatible. - switch (left_argument_type->getTypeID()) { - case kInt: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kInt, kLong, kFloat, kDouble); - case kLong: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kLong, kDouble); - case kFloat: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kFloat, kDouble); - case kDouble: - return (result_type->getTypeID() == kDouble); - case kDate: - return (result_type->getTypeID() == kDate); - case kDatetime: - return QUICKSTEP_EQUALS_ANY_CONSTANT( - result_type->getTypeID(), - kDatetime, kDatetimeInterval); - case kDatetimeInterval: - return (result_type->getTypeID() == kDatetimeInterval); - case kYearMonthInterval: - return (result_type->getTypeID() == kYearMonthInterval); - default: - return false; - } - } - - // Left and right (subtrahend and minuend) argument types are both known. - const Type *actual_result_type = resultTypeForArgumentTypes(*left_argument_type, - *right_argument_type); - if (actual_result_type == nullptr) { - // Both argument Types are known, but this operation is NOT applicable to - // them. No matter what the result_type is, the signature is not - // plausible. - return false; - } else if (result_type == nullptr) { - return true; - } else { - // Check if result type matches. - return result_type->equals(*actual_result_type); - } - } -} - -std::pair<const Type*, const Type*> SubtractBinaryOperation::pushDownTypeHint( - const Type *result_type_hint) const { - if (result_type_hint == nullptr) { - return std::pair<const Type*, const Type*>(nullptr, nullptr); - } - - switch (result_type_hint->getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: - case kYearMonthInterval: - return std::pair<const Type*, const Type*>(result_type_hint, result_type_hint); - case kDate: - // Left should be a Date, right should be YearMonthInterval. - return std::pair<const Type *, const Type *>( - result_type_hint, &TypeFactory::GetType(kYearMonthInterval, true)); - case kDatetime: - // Left should be a Datetime, right may be either interval type. - return std::pair<const Type*, const Type*>(result_type_hint, nullptr); - case kDatetimeInterval: - // Ambiguous: could be subtracting two Datetimes or two DatetimeIntervals. - return std::pair<const Type*, const Type*>(nullptr, nullptr); - default: - // Inapplicable. - return std::pair<const Type*, const Type*>(nullptr, nullptr); - } -} - -TypedValue SubtractBinaryOperation::applyToChecked(const TypedValue &left, - const Type &left_type, - const TypedValue &right, - const Type &right_type) const { - switch (left_type.getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: { - if (right_type.getSuperTypeID() == Type::kNumeric) { - return applyToCheckedNumericHelper<SubtractFunctor>(left, left_type, - right, right_type); - } - break; - } - case kDate: { - if (right_type.getTypeID() == kYearMonthInterval) { - if (left.isNull() || right.isNull()) { - return TypedValue(kDate); - } - - return TypedValue(left.getLiteral<DateLit>() - right.getLiteral<YearMonthIntervalLit>()); - } - break; - } - case kDatetime: { - if (right_type.getTypeID() == kDatetime) { - // NOTE(zuyu): The result type of the Subtract between two Datetimes is DatetimeInterval, - // instead of YearMonthInterval. - if (left.isNull() || right.isNull()) { - return TypedValue(kDatetimeInterval); - } - - return TypedValue(left.getLiteral<DatetimeLit>() - right.getLiteral<DatetimeLit>()); - } else if (right_type.getTypeID() == kDatetimeInterval) { - if (left.isNull() || right.isNull()) { - return TypedValue(kDatetime); - } - - return TypedValue(left.getLiteral<DatetimeLit>() - right.getLiteral<DatetimeIntervalLit>()); - } else if (right_type.getTypeID() == kYearMonthInterval) { - if (left.isNull() || right.isNull()) { - return TypedValue(kDatetime); - } - - return TypedValue(left.getLiteral<DatetimeLit>() - right.getLiteral<YearMonthIntervalLit>()); - } - break; - } - case kDatetimeInterval: { - if (right_type.getTypeID() == kDatetimeInterval) { - if (left.isNull() || right.isNull()) { - return TypedValue(kDatetimeInterval); - } - - return TypedValue(left.getLiteral<DatetimeIntervalLit>() - right.getLiteral<DatetimeIntervalLit>()); - } - break; - } - case kYearMonthInterval: { - if (right_type.getTypeID() == kYearMonthInterval) { - if (left.isNull() || right.isNull()) { - return TypedValue(kYearMonthInterval); - } - - return TypedValue(left.getLiteral<YearMonthIntervalLit>() - right.getLiteral<YearMonthIntervalLit>()); - } - break; - } - default: - break; - } - - LOG(FATAL) << "Can not apply " << getName() << " to arguments of types " - << left_type.getName() << " and " << right_type.getName(); -} - -UncheckedBinaryOperator* SubtractBinaryOperation::makeUncheckedBinaryOperatorForTypes(const Type &left, - const Type &right) const { - switch (left.getTypeID()) { - case kInt: - case kLong: - case kFloat: - case kDouble: { - if (right.getSuperTypeID() == Type::kNumeric) { - return makeNumericBinaryOperatorOuterHelper<SubtractArithmeticUncheckedBinaryOperator>(left, right); - } - break; - } - case kDate: { - if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper< - SubtractArithmeticUncheckedBinaryOperator, - DateType, - DateLit, - YearMonthIntervalLit>(left, right); - } - break; - } - case kDatetime: { - if (right.getTypeID() == kDatetime) { - // NOTE(zuyu): The result type of the Subtract between two Datetimes is DatetimeInterval, - // instead of YearMonthInterval. - return makeDateBinaryOperatorOuterHelper<SubtractArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DatetimeLit, DatetimeLit>(left, right); - } else if (right.getTypeID() == kDatetimeInterval) { - return makeDateBinaryOperatorOuterHelper<SubtractArithmeticUncheckedBinaryOperator, - DatetimeType, - DatetimeLit, DatetimeIntervalLit>(left, right); - } else if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper<SubtractArithmeticUncheckedBinaryOperator, - DatetimeType, - DatetimeLit, YearMonthIntervalLit>(left, right); - } - break; - } - case kDatetimeInterval: { - if (right.getTypeID() == kDatetimeInterval) { - return makeDateBinaryOperatorOuterHelper<SubtractArithmeticUncheckedBinaryOperator, - DatetimeIntervalType, - DatetimeIntervalLit, DatetimeIntervalLit>(left, right); - } - break; - } - case kYearMonthInterval: { - if (right.getTypeID() == kYearMonthInterval) { - return makeDateBinaryOperatorOuterHelper<SubtractArithmeticUncheckedBinaryOperator, - YearMonthIntervalType, - YearMonthIntervalLit, YearMonthIntervalLit>(left, right); - } - break; - } - default: - break; - } - - throw OperationInapplicableToType(getName(), 2, left.getName().c_str(), right.getName().c_str()); -} - -} // namespace quickstep http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/binary_operations/SubtractBinaryOperation.hpp ---------------------------------------------------------------------- diff --git a/types/operations/binary_operations/SubtractBinaryOperation.hpp b/types/operations/binary_operations/SubtractBinaryOperation.hpp deleted file mode 100644 index 8e54362..0000000 --- a/types/operations/binary_operations/SubtractBinaryOperation.hpp +++ /dev/null @@ -1,93 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - **/ - -#ifndef QUICKSTEP_TYPES_OPERATIONS_BINARY_OPERATIONS_SUBTRACT_BINARY_OPERATION_HPP_ -#define QUICKSTEP_TYPES_OPERATIONS_BINARY_OPERATIONS_SUBTRACT_BINARY_OPERATION_HPP_ - -#include <utility> - -#include "types/TypedValue.hpp" -#include "types/operations/binary_operations/ArithmeticBinaryOperation.hpp" -#include "types/operations/binary_operations/BinaryOperationID.hpp" -#include "utility/Macros.hpp" - -namespace quickstep { - -class Type; -class UncheckedBinaryOperator; - -/** \addtogroup Types - * @{ - */ - -/** - * @brief The BinaryOperation for subtraction. - * - * @note SubtractBinaryOperation is not commutative: the left argument is the - * minuend and the right argument is the subtrahend. - **/ -class SubtractBinaryOperation : public ArithmeticBinaryOperation { - public: - /** - * @brief Get a reference to the singleton instance of this Operation. - * - * @return A reference to the singleton instance of this Operation. - **/ - static const SubtractBinaryOperation& Instance() { - static SubtractBinaryOperation instance; - return instance; - } - - bool canApplyToTypes(const Type &left, - const Type &right) const override; - - const Type* resultTypeForArgumentTypes(const Type &left, - const Type &right) const override; - - const Type* resultTypeForPartialArgumentTypes(const Type *left, - const Type *right) const override; - - bool partialTypeSignatureIsPlausible(const Type *result_type, - const Type *left_argument_type, - const Type *right_argument_type) const override; - - std::pair<const Type*, const Type*> pushDownTypeHint( - const Type *result_type_hint) const override; - - TypedValue applyToChecked(const TypedValue &left, - const Type &left_type, - const TypedValue &right, - const Type &right_type) const override; - - UncheckedBinaryOperator *makeUncheckedBinaryOperatorForTypes(const Type &left, - const Type &right) const override; - - private: - SubtractBinaryOperation() - : ArithmeticBinaryOperation(BinaryOperationID::kSubtract) { - } - - DISALLOW_COPY_AND_ASSIGN(SubtractBinaryOperation); -}; - -/** @} */ - -} // namespace quickstep - -#endif // QUICKSTEP_TYPES_OPERATIONS_BINARY_OPERATIONS_SUBTRACT_BINARY_OPERATION_HPP_ http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/ArithmeticUnaryOperations.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/ArithmeticUnaryOperations.hpp b/types/operations/unary_operations/ArithmeticUnaryOperations.hpp index 089b5a1..4c212c0 100644 --- a/types/operations/unary_operations/ArithmeticUnaryOperations.hpp +++ b/types/operations/unary_operations/ArithmeticUnaryOperations.hpp @@ -28,9 +28,8 @@ #include "types/IntType.hpp" #include "types/LongType.hpp" #include "types/YearMonthIntervalType.hpp" -#include "types/operations/unary_operations/UnaryOperation.hpp" +#include "types/operations/OperationUtil.hpp" #include "types/operations/unary_operations/UnaryOperationWrapper.hpp" -#include "utility/Macros.hpp" namespace quickstep { @@ -44,19 +43,35 @@ struct NegateFunctor : public UnaryFunctor<ArgumentT, ResultT> { const typename ArgumentT::cpptype &argument) const { return -argument; } - inline std::string getName() const { - return "Negate"; + inline static std::string GetName() { + return "-"; } }; -using ArithmeticUnaryFunctorPack = UnaryFunctorPack< +template <typename ArgumentT> +struct SgnFunctor : public UnaryFunctor<ArgumentT, IntType> { + inline int apply(const typename ArgumentT::cpptype &argument) const { + return (argument > 0) - (argument < 0); + } + inline static std::string GetName() { + return "Sgn"; + } +}; + +using ArithmeticUnaryFunctorPack = FunctorPack< // negate NegateFunctor<IntType, IntType>, NegateFunctor<LongType, LongType>, NegateFunctor<FloatType, FloatType>, NegateFunctor<DoubleType, DoubleType>, NegateFunctor<DatetimeIntervalType, DatetimeIntervalType>, - NegateFunctor<YearMonthIntervalType, YearMonthIntervalType> + NegateFunctor<YearMonthIntervalType, YearMonthIntervalType>, + +// sgn (Sign of a numeric value) + SgnFunctor<IntType>, + SgnFunctor<LongType>, + SgnFunctor<FloatType>, + SgnFunctor<DoubleType> >; /** @} */ http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/AsciiStringUnaryOperations.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/AsciiStringUnaryOperations.hpp b/types/operations/unary_operations/AsciiStringUnaryOperations.hpp new file mode 100644 index 0000000..8fb2b8f --- /dev/null +++ b/types/operations/unary_operations/AsciiStringUnaryOperations.hpp @@ -0,0 +1,122 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + **/ + +#ifndef QUICKSTEP_TYPES_OPERATIONS_UNARY_OPERATIONS_ASCII_STRING_UNARY_OPERATIONS_HPP_ +#define QUICKSTEP_TYPES_OPERATIONS_UNARY_OPERATIONS_ASCII_STRING_UNARY_OPERATIONS_HPP_ + +#include <cctype> +#include <cstring> +#include <string> + +#include "types/CharType.hpp" +#include "types/IntType.hpp" +#include "types/Type.hpp" +#include "types/TypeFactory.hpp" +#include "types/TypeID.hpp" +#include "types/VarCharType.hpp" +#include "types/operations/OperationUtil.hpp" +#include "types/operations/unary_operations/UnaryOperationWrapper.hpp" +#include "types/port/strnlen.hpp" +#include "utility/TemplateUtil.hpp" + +namespace quickstep { + +/** \addtogroup Types + * @{ + */ + +template <typename ArgumentT> +struct AsciiStringLengthFunctor : public UnaryFunctor<ArgumentT, IntType> { + explicit AsciiStringLengthFunctor(const ArgumentT &argument_type) + : max_string_length_(argument_type.getStringLength()) {} + inline int apply(const void *argument) const { + return strnlen(static_cast<const char*>(argument), max_string_length_); + } + inline int apply(const TypedValue &argument) const { + DCHECK(argument.getTypeID() == kVarChar); + return std::strlen(static_cast<const char*>(argument.getOutOfLineData())); + } + inline static std::string GetName() { + return "length"; + } + const std::size_t max_string_length_; +}; + +template <typename ArgumentT, int transform(int), typename FunctorNameT> +struct AsciiStringTranformFunctor : public UnaryFunctor<ArgumentT, ArgumentT> { + explicit AsciiStringTranformFunctor(const ArgumentT &argument_type) + : max_string_length_(argument_type.getStringLength()) {} + inline void apply(const void *argument, void *result) const { + DCHECK(ArgumentT::kStaticTypeID == kChar); + const char *argument_str = static_cast<const char*>(argument); + char *result_str = static_cast<char*>(result); + for (std::size_t i = 0; i < max_string_length_; ++i) { + if ((result_str[i] = transform(argument_str[i])) == 0) { + break; + } + } + } + inline TypedValue apply(const TypedValue &argument) const { + DCHECK(argument.getTypeID() == kVarChar); + const char *argument_str = static_cast<const char*>(argument.getOutOfLineData()); + const std::size_t length = argument.getDataSize(); + char *buf = static_cast<char*>(std::malloc(length)); + + for (std::size_t i = 0; i < length; ++i) { + buf[i] = transform(argument_str[i]); + } + return TypedValue::CreateWithOwnedData(kVarChar, buf, length); + } + inline static std::string GetName() { + return FunctorNameT::ToString(); + } + inline static const Type* GetResultType(const Type &argument_type) { + DCHECK(argument_type.getTypeID() == ArgumentT::kStaticTypeID); + return &argument_type; + } + const std::size_t max_string_length_; +}; + +template <typename ArgumentT> +using AsciiStringToLowerCaseFunctor = + AsciiStringTranformFunctor<ArgumentT, std::tolower, + StringLiteral<'t', 'o', 'l', 'o', 'w', 'e', 'r'>>; + +template <typename ArgumentT> +using AsciiStringToUpperCaseFunctor = + AsciiStringTranformFunctor<ArgumentT, std::toupper, + StringLiteral<'t', 'o', 'u', 'p', 'p', 'e', 'r'>>; + +using AsciiStringUnaryFunctorPack = FunctorPack< +// length + AsciiStringLengthFunctor<CharType>, + AsciiStringLengthFunctor<VarCharType>, +// tolower + AsciiStringToLowerCaseFunctor<CharType>, + AsciiStringToLowerCaseFunctor<VarCharType>, +// toupper + AsciiStringToUpperCaseFunctor<CharType>, + AsciiStringToUpperCaseFunctor<VarCharType> +>; + +/** @} */ + +} // namespace quickstep + +#endif // QUICKSTEP_TYPES_OPERATIONS_UNARY_OPERATIONS_ASCII_STRING_UNARY_OPERATIONS_HPP_ http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/CMakeLists.txt ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/CMakeLists.txt b/types/operations/unary_operations/CMakeLists.txt index fca7070..0f5ea60 100644 --- a/types/operations/unary_operations/CMakeLists.txt +++ b/types/operations/unary_operations/CMakeLists.txt @@ -19,6 +19,9 @@ add_library(quickstep_types_operations_unaryoperations_ArithmeticUnaryOperations ../../../empty_src.cpp ArithmeticUnaryOperations.hpp) +add_library(quickstep_types_operations_unaryoperations_AsciiStringUnaryOperations + ../../../empty_src.cpp + AsciiStringUnaryOperations.hpp) add_library(quickstep_types_operations_unaryoperations_CMathUnaryOperations ../../../empty_src.cpp CMathUnaryOperations.hpp) @@ -30,9 +33,6 @@ add_library(quickstep_types_operations_unaryoperations_SubstringOperation SubstringOperation.cpp SubstringOperation.hpp) add_library(quickstep_types_operations_unaryoperations_UnaryOperation UnaryOperation.cpp UnaryOperation.hpp) -add_library(quickstep_types_operations_unaryoperations_UnaryOperationFactory - UnaryOperationFactory.cpp - UnaryOperationFactory.hpp) add_library(quickstep_types_operations_unaryoperations_UnaryOperationWrapper ../../../empty_src.cpp UnaryOperationWrapper.hpp) @@ -45,54 +45,55 @@ target_link_libraries(quickstep_types_operations_unaryoperations_ArithmeticUnary quickstep_types_FloatType quickstep_types_IntType quickstep_types_LongType - quickstep_types_Type - quickstep_types_TypeErrors - quickstep_types_TypeID - quickstep_types_TypedValue quickstep_types_YearMonthIntervalType - quickstep_types_operations_unaryoperations_UnaryOperation - quickstep_utility_EqualsAnyConstant - quickstep_utility_Macros) + quickstep_types_operations_OperationUtil + quickstep_types_operations_unaryoperations_UnaryOperationWrapper) +target_link_libraries(quickstep_types_operations_unaryoperations_AsciiStringUnaryOperations + quickstep_types_CharType + quickstep_types_IntType + quickstep_types_VarType + quickstep_types_operations_unaryoperations_UnaryOperationWrapper) target_link_libraries(quickstep_types_operations_unaryoperations_CMathUnaryOperations quickstep_types_DoubleType quickstep_types_FloatType quickstep_types_IntType quickstep_types_LongType + quickstep_types_operations_OperationUtil quickstep_types_operations_unaryoperations_UnaryOperationWrapper quickstep_utility_TemplateUtil) target_link_libraries(quickstep_types_operations_unaryoperations_CastOperation glog - quickstep_catalog_CatalogTypedefs - quickstep_storage_ValueAccessor - quickstep_storage_ValueAccessorUtil + quickstep_types_CharType quickstep_types_DoubleType quickstep_types_FloatType quickstep_types_IntType quickstep_types_LongType quickstep_types_Type + quickstep_types_TypeFactory quickstep_types_TypeID + quickstep_types_TypeUtil quickstep_types_TypedValue - quickstep_types_containers_ColumnVector - quickstep_types_operations_Operation_proto + quickstep_types_VarCharType quickstep_types_operations_unaryoperations_UnaryOperation - quickstep_utility_Macros) + quickstep_types_operations_unaryoperations_UnaryOperationWrapper + quickstep_types_port_strnlen + quickstep_utility_EqualsAnyConstant + quickstep_utility_Macros + quickstep_utility_StringUtil) target_link_libraries(quickstep_types_operations_unaryoperations_DateExtractOperation glog - quickstep_catalog_CatalogTypedefs - quickstep_storage_StorageBlockInfo - quickstep_storage_ValueAccessor - quickstep_storage_ValueAccessorUtil + quickstep_types_DateType quickstep_types_DatetimeLit + quickstep_types_DatetimeType quickstep_types_IntType quickstep_types_LongType quickstep_types_Type - quickstep_types_TypeFactory quickstep_types_TypeID quickstep_types_TypedValue - quickstep_types_containers_ColumnVector - quickstep_types_operations_Operation_proto quickstep_types_operations_unaryoperations_UnaryOperation - quickstep_utility_Macros) + quickstep_types_operations_unaryoperations_UnaryOperationWrapper + quickstep_utility_Macros + quickstep_utility_StringUtil) target_link_libraries(quickstep_types_operations_unaryoperations_SubstringOperation quickstep_catalog_CatalogTypedefs quickstep_storage_ValueAccessor @@ -119,48 +120,31 @@ target_link_libraries(quickstep_types_operations_unaryoperations_UnaryOperation quickstep_types_operations_OperationSignature quickstep_types_operations_Operation_proto quickstep_utility_Macros) -target_link_libraries(quickstep_types_operations_unaryoperations_UnaryOperationFactory - glog - quickstep_types_operations_OperationSignature - quickstep_types_operations_unaryoperations_ArithmeticUnaryOperations - quickstep_types_operations_unaryoperations_CMathUnaryOperations - quickstep_types_operations_unaryoperations_CastOperation - quickstep_types_operations_unaryoperations_DateExtractOperation - quickstep_types_operations_unaryoperations_SubstringOperation - quickstep_types_operations_unaryoperations_UnaryOperation - quickstep_types_operations_unaryoperations_UnaryOperationWrapper - quickstep_utility_HashPair - quickstep_utility_Macros - quickstep_utility_StringUtil) target_link_libraries(quickstep_types_operations_unaryoperations_UnaryOperationWrapper glog quickstep_catalog_CatalogTypedefs quickstep_storage_ValueAccessor quickstep_storage_ValueAccessorUtil - quickstep_types_CharType - quickstep_types_IntType - quickstep_types_LongType quickstep_types_Type quickstep_types_TypeFactory quickstep_types_TypeID quickstep_types_TypedValue - quickstep_types_VarCharType quickstep_types_containers_ColumnVector - quickstep_types_operations_Operation quickstep_types_operations_OperationSignature - quickstep_types_operations_Operation_proto + quickstep_types_operations_OperationUtil + quickstep_types_operations_unaryoperations_UnaryOperation quickstep_utility_Macros) # Module all-in-one library: add_library(quickstep_types_operations_unaryoperations ../../../empty_src.cpp) target_link_libraries(quickstep_types_operations_unaryoperations quickstep_types_operations_unaryoperations_ArithmeticUnaryOperations + quickstep_types_operations_unaryoperations_AsciiStringUnaryOperations quickstep_types_operations_unaryoperations_CMathUnaryOperations quickstep_types_operations_unaryoperations_CastOperation quickstep_types_operations_unaryoperations_DateExtractOperation quickstep_types_operations_unaryoperations_SubstringOperation quickstep_types_operations_unaryoperations_UnaryOperation - quickstep_types_operations_unaryoperations_UnaryOperationFactory quickstep_types_operations_unaryoperations_UnaryOperationWrapper) # Tests: @@ -189,7 +173,6 @@ target_link_libraries(UnaryOperation_tests quickstep_types_operations_unaryoperations_CastOperation quickstep_types_operations_unaryoperations_DateExtractOperation quickstep_types_operations_unaryoperations_UnaryOperation - quickstep_types_operations_unaryoperations_UnaryOperationFactory quickstep_utility_EqualsAnyConstant quickstep_utility_Macros) add_test(UnaryOperation_tests UnaryOperation_tests) http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/CMathUnaryOperations.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/CMathUnaryOperations.hpp b/types/operations/unary_operations/CMathUnaryOperations.hpp index 7d1625b..43f771e 100644 --- a/types/operations/unary_operations/CMathUnaryOperations.hpp +++ b/types/operations/unary_operations/CMathUnaryOperations.hpp @@ -27,6 +27,7 @@ #include "types/FloatType.hpp" #include "types/IntType.hpp" #include "types/LongType.hpp" +#include "types/operations/OperationUtil.hpp" #include "types/operations/unary_operations/UnaryOperationWrapper.hpp" #include "utility/TemplateUtil.hpp" @@ -45,7 +46,7 @@ struct CMathUnaryFunctorWrapper { const typename ArgumentT::cpptype &argument) const { return f(argument); } - inline std::string getName() const { + inline static std::string GetName() { return FunctorNameT::ToString(); } }; @@ -59,7 +60,7 @@ template <typename ArgumentT, typename ReturnT, using CMathUnaryFunctor = typename CMathUnaryFunctorWrapper<ArgumentT, ReturnT, f, FunctorNameT>::type; -using CMathUnaryFunctorPack = UnaryFunctorPack< +using CMathUnaryFunctorPack = FunctorPack< // abs CMathUnaryFunctor<IntType, IntType, std::abs, StringLiteral<'a','b','s'>>, http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/CastOperation.cpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/CastOperation.cpp b/types/operations/unary_operations/CastOperation.cpp index ef5b8f8..b240b23 100644 --- a/types/operations/unary_operations/CastOperation.cpp +++ b/types/operations/unary_operations/CastOperation.cpp @@ -53,26 +53,28 @@ struct NumericCastToNumericFunctor }; template <typename ArgumentT, typename ResultT> -class NumericCastToAsciiStringFunctor : public UnaryFunctor<ArgumentT, ResultT> { +class CastToAsciiStringFunctor : public UnaryFunctor<ArgumentT, ResultT> { public: - explicit NumericCastToAsciiStringFunctor(const std::size_t max_length) - : max_length_(max_length) {} + explicit CastToAsciiStringFunctor(const ArgumentT &argument_type, + const std::size_t max_string_length) + : argument_type_(argument_type), + max_string_length_(max_string_length) {} inline void apply(const typename ArgumentT::cpptype &argument, void *result) const { - std::string str = std::to_string(argument); + std::string str = argument_type_.printValueToString(TypedValue(argument)); const std::size_t str_len = str.length(); - if (str_len < max_length_) { + if (str_len < max_string_length_) { std::memcpy(result, str.c_str(), str_len); static_cast<char *>(result)[str_len] = 0; } else { - std::memcpy(result, str.c_str(), max_length_); + std::memcpy(result, str.c_str(), max_string_length_); } } inline TypedValue apply(const typename ArgumentT::cpptype &argument) const { - std::string str = std::to_string(argument); - const std::size_t len = std::min(str.length(), max_length_); + std::string str = argument_type_.printValueToString(TypedValue(argument)); + const std::size_t len = std::min(str.length(), max_string_length_); const std::size_t buf_len = len + 1; char *buf = static_cast<char *>(std::malloc(buf_len)); @@ -82,10 +84,10 @@ class NumericCastToAsciiStringFunctor : public UnaryFunctor<ArgumentT, ResultT> } private: - const std::size_t max_length_; + const ArgumentT &argument_type_; + const std::size_t max_string_length_; }; - template <typename ResultCppType> ResultCppType CastStringToNumericImpl(const char *str); @@ -110,8 +112,8 @@ template <typename ArgumentT, typename ResultT, typename ResultT::cpptype f(const char*)> struct AsciiStringCastToNumericFunctor : public UnaryFunctor<ArgumentT, ResultT> { - explicit AsciiStringCastToNumericFunctor(const std::size_t max_length) - : max_length_(max_length) {} + explicit AsciiStringCastToNumericFunctor(const std::size_t max_string_length) + : max_string_length_(max_string_length) {} inline typename ResultT::cpptype apply(const TypedValue &argument) const { return f(static_cast<const char*>(argument.getDataPtr())); @@ -119,12 +121,12 @@ struct AsciiStringCastToNumericFunctor inline typename ResultT::cpptype apply(const void *argument) const { const char *str = static_cast<const char*>(argument); - const std::string value(str, strnlen(str, max_length_)); + const std::string value(str, strnlen(str, max_string_length_)); return f(value.c_str()); } private: - const std::size_t max_length_; + const std::size_t max_string_length_; }; template <typename ArgumentT, typename ResultT> @@ -217,8 +219,9 @@ UncheckedUnaryOperator* CastOperation::makeUncheckedUnaryOperator( using ResultT = typename TypeGenerator<decltype(result_tid)::value>::type; return new UncheckedUnaryOperatorWrapperCodegen< - NumericCastToAsciiStringFunctor<ArgumentT, ResultT>>( + CastToAsciiStringFunctor<ArgumentT, ResultT>>( type, *result_type, + static_cast<const ArgumentT&>(type), static_cast<const ResultT*>(result_type)->getStringLength()); }); } http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/CastOperation.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/CastOperation.hpp b/types/operations/unary_operations/CastOperation.hpp index 23dbec2..713a89c 100644 --- a/types/operations/unary_operations/CastOperation.hpp +++ b/types/operations/unary_operations/CastOperation.hpp @@ -24,6 +24,7 @@ #include <map> #include <string> #include <utility> +#include <vector> #include "types/IntType.hpp" #include "types/Type.hpp" @@ -77,7 +78,7 @@ class CastOperation : public UnaryOperation { const std::vector<TypedValue> &static_arguments, std::string *message) const override { DCHECK_EQ(1u, static_arguments.size()); - if (parseType(static_arguments.front()) == nullptr) { + if (getResultTypeInternal(type, static_arguments.front()) == nullptr) { *message = "Invalid target type for CAST"; return false; } @@ -88,14 +89,10 @@ class CastOperation : public UnaryOperation { const Type &type, const std::vector<TypedValue> &static_arguments) const override { DCHECK_EQ(1u, static_arguments.size()); - const Type *target_type = parseType(static_arguments.front()); - + const Type *target_type = + getResultTypeInternal(type, static_arguments.front()); DCHECK(target_type != nullptr); - if (type.isNullable()) { - return &target_type->getNullableVersion(); - } else { - return target_type; - } + return target_type; } UncheckedUnaryOperator* makeUncheckedUnaryOperator( @@ -103,11 +100,17 @@ class CastOperation : public UnaryOperation { const std::vector<TypedValue> &static_arguments) const override; private: - static const Type* parseType(const TypedValue &type_arg) { + static const Type* getResultTypeInternal(const Type &type, + const TypedValue &type_arg) { DCHECK(type_arg.getTypeID() == kVarChar); const std::string type_str = ToLower(std::string(static_cast<const char*>(type_arg.getOutOfLineData()))); + if (type_str == "text") { + return &TypeFactory::GetType( + kVarChar, type.getPrintWidth(), type.isNullable()); + } + const re2::StringPiece type_piece(type_str); std::string type_name; std::string length_str; @@ -130,7 +133,9 @@ class CastOperation : public UnaryOperation { TypedValue length_value; if (IntType::InstanceNonNullable().parseValueFromString(length_str, &length_value)) { return &TypeFactory::GetType( - it->second, static_cast<std::size_t>(length_value.getLiteral<int>())); + it->second, + static_cast<std::size_t>(length_value.getLiteral<int>()), + type.isNullable()); } } return nullptr; http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/DateExtractOperation.cpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/DateExtractOperation.cpp b/types/operations/unary_operations/DateExtractOperation.cpp index c09b400..f95e109 100644 --- a/types/operations/unary_operations/DateExtractOperation.cpp +++ b/types/operations/unary_operations/DateExtractOperation.cpp @@ -38,8 +38,7 @@ namespace quickstep { -struct DateExtractFunctor - : public UnaryFunctor<DateType, IntType> { +struct DateExtractFunctor : public UnaryFunctor<DateType, IntType> { template <typename DateExtractUnitT> inline int apply(const DateLit &argument) const { switch (DateExtractUnitT::value) { @@ -55,8 +54,7 @@ struct DateExtractFunctor } }; -struct DatetimeExtractFunctor - : public UnaryFunctor<DatetimeType, IntType> { +struct DatetimeExtractFunctor : public UnaryFunctor<DatetimeType, IntType> { template <typename DateExtractUnitT> inline std::int64_t apply(const DatetimeLit &argument) const { switch (DateExtractUnitT::value) { @@ -91,7 +89,8 @@ UncheckedUnaryOperator* DateExtractOperation::makeUncheckedUnaryOperator( const Type &type, const std::vector<TypedValue> &static_arguments) const { DCHECK_EQ(1u, static_arguments.size()); - DateExtractUnit unit = parseUnit(static_arguments.front()); + + const DateExtractUnit unit = parseUnit(static_arguments.front()); const Type *result_type = getResultType(type, static_arguments); if (type.getTypeID() == kDate) { http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/DateExtractOperation.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/DateExtractOperation.hpp b/types/operations/unary_operations/DateExtractOperation.hpp index 00948a4..577e924 100644 --- a/types/operations/unary_operations/DateExtractOperation.hpp +++ b/types/operations/unary_operations/DateExtractOperation.hpp @@ -23,20 +23,11 @@ #include <cstdint> #include <string> -#ifdef QUICKSTEP_ENABLE_VECTOR_COPY_ELISION_JOIN -#include <utility> -#include <vector> - -#include "storage/StorageBlockInfo.hpp" -#endif // QUICKSTEP_ENABLE_VECTOR_COPY_ELISION_JOIN - -#include "catalog/CatalogTypedefs.hpp" #include "types/IntType.hpp" #include "types/LongType.hpp" #include "types/Type.hpp" #include "types/TypeID.hpp" #include "types/TypedValue.hpp" -#include "types/operations/Operation.pb.h" #include "types/operations/unary_operations/UnaryOperation.hpp" #include "utility/Macros.hpp" #include "utility/StringUtil.hpp" @@ -69,22 +60,37 @@ class DateExtractOperation : public UnaryOperation { } std::vector<OperationSignaturePtr> getSignatures() const override { - const std::vector<TypeID> target_type_carrier = { kVarChar }; + const std::vector<TypeID> unit_carrier = { kVarChar }; return { - OperationSignature::Create(getName(), {kDate}, target_type_carrier), - OperationSignature::Create(getName(), {kDatetime}, target_type_carrier) + OperationSignature::Create(getName(), {kDate}, unit_carrier), + OperationSignature::Create(getName(), {kDatetime}, unit_carrier) }; } bool canApplyTo(const Type &type, const std::vector<TypedValue> &static_arguments, std::string *message) const override { + DCHECK(type.getTypeID() == kDate || type.getTypeID() == kDatetime); DCHECK_EQ(1u, static_arguments.size()); - if (parseUnit(static_arguments.front()) == DateExtractUnit::kInvalid) { - *message = "Invalid extraction unit for DateExtract"; - return false; + + const DateExtractUnit unit = parseUnit(static_arguments.front()); + switch (unit) { + case DateExtractUnit::kYear: // Fall through + case DateExtractUnit::kMonth: + case DateExtractUnit::kDay: + return true; + case DateExtractUnit::kHour: // Fall through + case DateExtractUnit::kMinute: + case DateExtractUnit::kSecond: + if (type.getTypeID() == kDate) { + *message = "Invalid extraction unit for argument of DATE type"; + } else { + return true; + } + default: + *message = "Invalid extraction unit for DateExtract"; + return false; } - return true; } const Type* getResultType( http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/SubstringOperation.cpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/SubstringOperation.cpp b/types/operations/unary_operations/SubstringOperation.cpp index 408ea2d..3d0d139 100644 --- a/types/operations/unary_operations/SubstringOperation.cpp +++ b/types/operations/unary_operations/SubstringOperation.cpp @@ -32,7 +32,6 @@ #include "types/TypedValue.hpp" #include "types/containers/ColumnVector.hpp" #include "types/containers/ColumnVectorUtil.hpp" -#include "types/operations/Operation.pb.h" #include "types/port/strnlen.hpp" #include "utility/TemplateUtil.hpp" @@ -160,37 +159,5 @@ ColumnVector* SubstringUncheckedOperator<null_terminated, } #endif -#ifdef QUICKSTEP_ENABLE_VECTOR_COPY_ELISION_JOIN -template <bool null_terminated, bool input_nullable> -ColumnVector* SubstringUncheckedOperator<null_terminated, - input_nullable> - ::applyToValueAccessorForJoin( - ValueAccessor *accessor, - const bool use_left_relation, - const attribute_id argument_attr_id, - const std::vector<std::pair<tuple_id, tuple_id>> &joined_tuple_ids) const { - return InvokeOnValueAccessorNotAdapter( - accessor, - [&](auto *accessor) -> ColumnVector* { // NOLINT(build/c++11) - NativeColumnVector *result = - new NativeColumnVector(result_type_, accessor->getNumTuples()); - - for (const std::pair<tuple_id, tuple_id> &joined_pair : joined_tuple_ids) { - const char *input_ptr = static_cast<const char *>( - accessor->template getUntypedValueAtAbsolutePosition<input_nullable>( - argument_attr_id, - use_left_relation ? joined_pair.first : joined_pair.second)); - - if (input_nullable && input_ptr == nullptr) { - result->appendNullValue(); - } else { - this->computeSubstring(input_ptr, - static_cast<char *>(result->getPtrForDirectWrite())); - } - } - return result; - }); -} -#endif } // namespace quickstep http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/UnaryOperation.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/UnaryOperation.hpp b/types/operations/unary_operations/UnaryOperation.hpp index 68dc993..70cb6f9 100644 --- a/types/operations/unary_operations/UnaryOperation.hpp +++ b/types/operations/unary_operations/UnaryOperation.hpp @@ -115,8 +115,6 @@ class UnaryOperation : public Operation { return getName(); } - virtual std::vector<OperationSignaturePtr> getSignatures() const = 0; - virtual bool canApplyTo(const Type &argument_type, const std::vector<TypedValue> &static_arguments, std::string *message) const = 0; @@ -129,9 +127,8 @@ class UnaryOperation : public Operation { const Type &argument_type, const std::vector<TypedValue> &static_arguments) const = 0; - bool canApplyTo( - const Type &argument_type, - const std::vector<TypedValue> &static_arguments) const { + bool canApplyTo(const Type &argument_type, + const std::vector<TypedValue> &static_arguments) const { std::string message; return canApplyTo(argument_type, static_arguments, &message); } http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/UnaryOperationFactory.cpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/UnaryOperationFactory.cpp b/types/operations/unary_operations/UnaryOperationFactory.cpp deleted file mode 100644 index cebf9e2..0000000 --- a/types/operations/unary_operations/UnaryOperationFactory.cpp +++ /dev/null @@ -1,74 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - **/ - -#include "types/operations/unary_operations/UnaryOperationFactory.hpp" - -#include <string> - -#include "types/operations/OperationSignature.hpp" -#include "types/operations/unary_operations/ArithmeticUnaryOperations.hpp" -#include "types/operations/unary_operations/CMathUnaryOperations.hpp" -#include "types/operations/unary_operations/CastOperation.hpp" -#include "types/operations/unary_operations/DateExtractOperation.hpp" -#include "types/operations/unary_operations/SubstringOperation.hpp" -#include "types/operations/unary_operations/UnaryOperationWrapper.hpp" -#include "utility/Macros.hpp" -#include "utility/StringUtil.hpp" - -namespace quickstep { - -UnaryOperationFactory::UnaryOperationFactory() { - registerUnaryOperation(UnaryOperationPtr(new CastOperation())); - registerUnaryOperation(UnaryOperationPtr(new DateExtractOperation())); - registerUnaryOperation(UnaryOperationPtr(new SubstringOperation())); - - registerUnaryOperationPack<CMathUnaryFunctorPack>(); - registerUnaryOperationPack<ArithmeticUnaryFunctorPack>(); -} - -void UnaryOperationFactory::registerUnaryOperation( - const UnaryOperationPtr &operation) { - for (const OperationSignaturePtr op_sig : operation->getSignatures()) { - const OperationSignaturePtr normalized_op_sig = - OperationSignature::Create(ToLower(op_sig->getName()), - op_sig->getArgumentTypeIDs(), - op_sig->getNumStaticArguments()); - - // TODO: print error message for collision - unary_operations_.emplace(normalized_op_sig, operation); - - const auto name_arity_pair = std::make_pair(normalized_op_sig->getName(), - normalized_op_sig->getArity()); - name_arity_index_[name_arity_pair].emplace(normalized_op_sig); - } -} - -template <typename UnaryOperationPackT> -void UnaryOperationFactory::registerUnaryOperationPack() { - for (const UnaryOperationPtr &operation : UnaryOperationPackT::GenerateAll()) { - registerUnaryOperation(operation); - } -} - -const UnaryOperationFactory& UnaryOperationFactory::Instance() { - static UnaryOperationFactory instance; - return instance; -} - -} // namespace quickstep http://git-wip-us.apache.org/repos/asf/incubator-quickstep/blob/4005df6e/types/operations/unary_operations/UnaryOperationFactory.hpp ---------------------------------------------------------------------- diff --git a/types/operations/unary_operations/UnaryOperationFactory.hpp b/types/operations/unary_operations/UnaryOperationFactory.hpp deleted file mode 100644 index c586b62..0000000 --- a/types/operations/unary_operations/UnaryOperationFactory.hpp +++ /dev/null @@ -1,97 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - **/ - -#ifndef QUICKSTEP_TYPES_OPERATIONS_UNARY_OPERATIONS_UNARY_OPERATION_FACTORY_HPP_ -#define QUICKSTEP_TYPES_OPERATIONS_UNARY_OPERATIONS_UNARY_OPERATION_FACTORY_HPP_ - -#include <set> -#include <unordered_map> -#include <utility> - -#include "types/operations/OperationSignature.hpp" -#include "types/operations/unary_operations/UnaryOperation.hpp" -#include "utility/HashPair.hpp" -#include "utility/Macros.hpp" - -#include "glog/logging.h" - -namespace quickstep { - -/** \addtogroup Types - * @{ - */ - -/** - * @brief All-static factory object that provides access to UnaryOperations. - **/ -class UnaryOperationFactory { - public: - static const UnaryOperationFactory& Instance(); - - inline bool hasUnaryOperation( - const OperationSignaturePtr &op_signature) const { - return unary_operations_.find(op_signature) != unary_operations_.end(); - } - - inline bool hasUnaryOperation(const std::string &name, - const std::size_t arity) const { - const auto it = name_arity_index_.find(std::make_pair(name, arity)); - return it != name_arity_index_.end(); - } - - inline const UnaryOperationPtr getUnaryOperation( - const OperationSignaturePtr &op_signature) const { - DCHECK(hasUnaryOperation(op_signature)); - return unary_operations_.at(op_signature); - } - - inline const std::set<OperationSignaturePtr, - OperationSignatureNumStaticArgumentsGreater>& - getUnaryOperations(const std::string &name, - const std::size_t arity) const { - DCHECK(hasUnaryOperation(name, arity)); - return name_arity_index_.at(std::make_pair(name, arity)); - } - - private: - UnaryOperationFactory(); - - void registerUnaryOperation(const UnaryOperationPtr &operation); - - template <typename UnaryOperationPackT> - void registerUnaryOperationPack(); - - std::unordered_map<OperationSignaturePtr, - UnaryOperationPtr, - OperationSignatureHash, - OperationSignatureEqual> unary_operations_; - - std::unordered_map< - std::pair<std::string, std::size_t>, - std::set<OperationSignaturePtr, - OperationSignatureNumStaticArgumentsGreater>> name_arity_index_; - - DISALLOW_COPY_AND_ASSIGN(UnaryOperationFactory); -}; - -/** @} */ - -} // namespace quickstep - -#endif // QUICKSTEP_TYPES_OPERATIONS_UNARY_OPERATIONS_UNARY_OPERATION_FACTORY_HPP_