blob: 74a90956714564511c9ccf9ee152685c1b05f32f [file] [log] [blame]
/**
* 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_STORAGE_AGGREGATION_UTIL_HPP_
#define QUICKSTEP_STORAGE_AGGREGATION_UTIL_HPP_
#include <type_traits>
#include "expressions/aggregation/AggregationID.hpp"
#include "expressions/aggregation/AggFunc.hpp"
#include "storage/ValueAccessor.hpp"
#include "storage/ValueAccessorMultiplexer.hpp"
#include "storage/ValueAccessorUtil.hpp"
#include "types/TypeID.hpp"
#include "types/Type.hpp"
#include "types/containers/ColumnVectorsValueAccessor.hpp"
#include "glog/logging.h"
namespace quickstep {
/** \addtogroup Storage
* @{
*/
template <typename T>
using remove_const_reference_t = std::remove_const_t<std::remove_reference_t<T>>;
template <typename FunctorT>
inline auto InvokeOnKeyType(const Type &type,
const FunctorT &functor) {
switch (type.getTypeID()) {
case TypeID::kInt:
return functor(static_cast<const IntType&>(type));
case TypeID::kLong:
return functor(static_cast<const LongType&>(type));
default:
LOG(FATAL) << "Not supported";
}
}
template <typename FunctorT>
inline auto InvokeOnType(const Type &type,
const FunctorT &functor) {
switch (type.getTypeID()) {
case TypeID::kInt:
return functor(static_cast<const IntType&>(type));
case TypeID::kLong:
return functor(static_cast<const LongType&>(type));
case TypeID::kFloat:
return functor(static_cast<const FloatType&>(type));
case TypeID::kDouble:
return functor(static_cast<const DoubleType&>(type));
default:
LOG(FATAL) << "Not supported";
}
}
template <typename FunctorT>
inline auto InvokeOnBool(const bool &val,
const FunctorT &functor) {
if (val) {
return functor(std::true_type());
} else {
return functor(std::false_type());
}
}
template <typename FunctorT>
inline auto InvokeOnBools(const bool &val1,
const bool &val2,
const FunctorT &functor) {
if (val1) {
if (val2) {
return functor(std::true_type(), std::true_type());
} else {
return functor(std::true_type(), std::false_type());
}
} else {
if (val2) {
return functor(std::false_type(), std::true_type());
} else {
return functor(std::false_type(), std::false_type());
}
}
}
template <typename FunctorT>
inline auto InvokeOnAggFunc(const AggregationID &agg_id,
const FunctorT &functor) {
switch (agg_id) {
case AggregationID::kSum: {
return functor(Sum());
}
default:
LOG(FATAL) << "Not supported";
}
}
template <typename FunctorT>
inline auto InvokeIf(const std::true_type &val,
const FunctorT &functor) {
return functor();
}
template <typename FunctorT>
inline void InvokeIf(const std::false_type &val,
const FunctorT &functor) {
}
//template <typename FunctorT>
//inline void InvokeOnAggFuncIfApplicableToArgType(
// const AggregationID &agg_id,
// const Type &arg_type,
// const FunctorT &functor) {
// InvokeOnAggFunc(
// agg_id,
// [&](const auto &agg_func) -> void {
// InvokeOnType(
// arg_type,
// [&](const auto &arg_type) -> void {
// using AggFuncT = std::remove_reference_t<decltype(agg_func)>;
// using ArgT = remove_const_reference_t<decltype(arg_type)>;
//
// InvokeIf(
// typename AggFuncT::template HasAtomicImpl<ArgT>(),
// [&]() -> void {
// functor(agg_func, arg_type);
// });
// });
// });
//}
template <typename FunctorT>
inline void InvokeOnAggFuncWithArgType(
const AggregationID &agg_id,
const Type &arg_type,
const FunctorT &functor) {
InvokeOnAggFunc(
agg_id,
[&](const auto &agg_func) -> void {
InvokeOnType(
arg_type,
[&](const auto &arg_type) -> void {
functor(agg_func, arg_type);
});
});
}
template <typename FunctorT>
inline auto InvokeOnTwoAccessors(
const ValueAccessorMultiplexer &accessor_mux,
const ValueAccessorSource &first_source,
const ValueAccessorSource &second_source,
const FunctorT &functor) {
ValueAccessor *base_accessor = accessor_mux.getBaseAccessor();
ColumnVectorsValueAccessor *derived_accessor =
static_cast<ColumnVectorsValueAccessor *>(accessor_mux.getDerivedAccessor());
InvokeOnAnyValueAccessor(
base_accessor,
[&](auto *accessor) {
if (first_source == ValueAccessorSource::kBase) {
if (second_source == ValueAccessorSource::kBase) {
return functor(std::false_type(), accessor, accessor);
} else {
return functor(std::true_type(), accessor, derived_accessor);
}
} else {
if (second_source == ValueAccessorSource::kBase) {
return functor(std::true_type(), derived_accessor, accessor);
} else {
return functor(std::false_type(), derived_accessor, derived_accessor);
}
}
});
}
} // namespace quickstep
#endif // QUICKSTEP_STORAGE_AGGREGATION_UTIL_HPP_