Compare commits

...

2 Commits

Author SHA1 Message Date
_Karasu_ 2b5fa34d96 施工阶段2 2022-08-04 17:13:13 +08:00
_Karasu_ d099ce41d3 施工阶段2 2022-08-04 17:13:06 +08:00
12 changed files with 403 additions and 783 deletions

View File

@ -1,6 +1,6 @@
cmake_minimum_required(VERSION 3.18) cmake_minimum_required(VERSION 3.18)
project(tmp_policy) project(tmp_policy)
set(CMAKE_CXX_STANDARD 14) set(CMAKE_CXX_STANDARD 17)
add_executable(tmp_policy main.cpp accpolicy.h policy_fundamentals.h) add_executable(tmp_policy main.cpp accpolicy.h policy_fundamentals.h accumulator.h)

102
accumulator.h Normal file
View File

@ -0,0 +1,102 @@
// tmp_policy
// Created by lucas on 22-8-4.
// Re-implementation of a typical policy architecture in C++ Template Meta-Programming.
#ifndef TMP_POLICY_ACCUMULATOR_H
#define TMP_POLICY_ACCUMULATOR_H
// A demo for integrating the policy architecture
// into your project.
#include <type_traits>
#include <cmath>
#include "accpolicy.h"
#include "policy_fundamentals.h"
// According to the C++ Standard,
// Direct use of static_assert(false) results in undefined behavior,
// so we define a type-dependent boolean variable whose value is false.
template <typename T>
constexpr bool DependencyFalse = false;
/**
* @brief class Accumulator - the class performs "accumulation"
* and it's behavior is controlled by policy objects.
* @tparam TPolicies The policy objects which control the class's behavior.
*/
template <typename ... TPolicies>
class Accumulator
{
// Put all the policy objects into a PolicyContainer.
using PolicyCont = PolicyContainer<TPolicies...>;
// Use PolicySelect Meta-Function to get the policy selection result.
using PSR = PolicySelect<PolicyCont, AccPolicy>;
// According to the policy selection result,
// we get the necessary information to control the Accumulator's behavior.
// AccuType - controls how the "accumulation" works; Add or Multiply?
using AccuType = typename PSR::AccuType;
// IsAve - returns the average or the original result?
static constexpr bool IsAve = PSR::IsAveValue;
// ResultType - What type do you expect the Accumulator to return?
using ResultType = typename PSR::ResultType;
public:
/**
* @brief eval - The function which does the "accumulation".
* @tparam TInput The type of parameter in - it will be judged by the compiler.
* @param in The input array which contains the elements waiting to be accumulated.
* It needs to support range-based for statement.
* @return The "accumulation" result. User-specified.
*/
template <typename TInput>
static auto eval(const TInput& in)
{
ResultType res{};
int count{};
// If we want to perform "add" ...
if constexpr (std::is_same<AccPolicy::AccuTypeCate::Add, AccuType>::value)
{
// Add the all elements to res ...
for (const auto& element: in)
{
res += element;
// ... and also records the number of elements.
count += 1;
}
// If we want to calculate average...
if constexpr (IsAve)
// ... calculates the average and returns.
return res / static_cast<ResultType>(count);
else
// ... if not, simply returns the sum.
return res;
}
// Or if we want to perform "multiply" ...
else if constexpr (std::is_same<AccPolicy::AccuTypeCate::Mul, AccuType>::value)
{
// Because 0 times any number equals 0 ...
// ... we need to give res an initial value.
res = 1;
// Multiply the all elements to res ...
for (const auto& element: in)
{
res *= element;
// ... and also records the number of elements.
count += 1;
}
// If we want to calculate average...
if constexpr (IsAve)
// ... calculates the average and returns.
return std::pow(res, 1.0 / static_cast<ResultType>(count));
else
// ... if not, simply returns the sum.
return res;
}
else
{
// We have triggered logic that should not be triggered ...
// ... the solution is to generate a compile error.
static_assert(DependencyFalse<AccuType>, "Invalid policy argument!");
}
}
};
#endif //TMP_POLICY_ACCUMULATOR_H

View File

@ -191,11 +191,11 @@
}, },
{ {
"name" : "HELPSTRING", "name" : "HELPSTRING",
"value" : "CXX compiler" "value" : "No help, variable specified on the command line."
} }
], ],
"type" : "STRING", "type" : "UNINITIALIZED",
"value" : "/usr/bin/clang++" "value" : "clang++"
}, },
{ {
"name" : "CMAKE_CXX_COMPILER_AR", "name" : "CMAKE_CXX_COMPILER_AR",
@ -319,11 +319,11 @@
}, },
{ {
"name" : "HELPSTRING", "name" : "HELPSTRING",
"value" : "C compiler" "value" : "No help, variable specified on the command line."
} }
], ],
"type" : "STRING", "type" : "UNINITIALIZED",
"value" : "/usr/bin/clang" "value" : "clang"
}, },
{ {
"name" : "CMAKE_C_COMPILER_AR", "name" : "CMAKE_C_COMPILER_AR",

View File

@ -1,759 +0,0 @@
{
"inputs" :
[
{
"path" : "CMakeLists.txt"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineSystem.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeSystem.cmake.in"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeSystem.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeUnixFindMake.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeSystemSpecificInitialize.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompilerId.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCompilerIdDetection.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/ADSP-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/ARMCC-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/ARMClang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/AppleClang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-DetermineCompilerInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Borland-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Bruce-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-DetermineCompilerInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Compaq-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Cray-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Embarcadero-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Fujitsu-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/FujitsuClang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/GHS-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/GNU-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/HP-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IAR-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Intel-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IntelLLVM-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/MSVC-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/NVHPC-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/NVIDIA-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/OpenWatcom-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/PGI-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/PathScale-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/SCO-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/SDCC-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/SunPro-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/TI-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/TinyCC-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/VisualAge-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IBMCPP-C-DetermineVersionInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Watcom-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/XL-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IBMCPP-C-DetermineVersionInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/XLClang-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/zOS-C-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IBMCPP-C-DetermineVersionInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeFindBinUtils.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-FindBinUtils.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCCompiler.cmake.in"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeCCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCXXCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-Determine-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompilerId.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCompilerIdDetection.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/ADSP-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/ARMCC-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/ARMClang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/AppleClang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-DetermineCompilerInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Borland-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-DetermineCompilerInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Comeau-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Compaq-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Cray-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Embarcadero-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Fujitsu-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/FujitsuClang-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/GHS-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/GNU-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/HP-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IAR-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Intel-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IntelLLVM-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/MSVC-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/NVHPC-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/NVIDIA-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/OpenWatcom-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/PGI-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/PathScale-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/SCO-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/SunPro-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/TI-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/VisualAge-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IBMCPP-CXX-DetermineVersionInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Watcom-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/XL-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IBMCPP-CXX-DetermineVersionInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/XLClang-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/zOS-CXX-DetermineCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/IBMCPP-CXX-DetermineVersionInternal.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeFindBinUtils.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-FindBinUtils.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCXXCompiler.cmake.in"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeCXXCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeSystemSpecificInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeGenericSystem.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeInitializeConfigs.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/UnixPaths.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeFindCodeBlocks.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeExtraGeneratorDetermineCompilerMacrosAndIncludeDirs.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/ProcessorCount.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeLanguageInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-C.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/CMakeCommonCompilerMacros.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/GNU.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/CMakeCommonCompilerMacros.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-Clang-C.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU-C.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCommonLanguageInclude.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeTestCCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeTestCompilerCommon.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompilerABI.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeParseImplicitIncludeInfo.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeParseImplicitLinkInfo.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeParseLibraryArchitecture.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeTestCompilerCommon.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCCompilerABI.c"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompileFeatures.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Internal/FeatureTesting.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCCompiler.cmake.in"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeCCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCXXInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeLanguageInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-Clang-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCommonLanguageInclude.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeTestCXXCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeTestCompilerCommon.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompilerABI.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeParseImplicitIncludeInfo.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeParseImplicitLinkInfo.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeParseLibraryArchitecture.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeTestCompilerCommon.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCXXCompilerABI.cpp"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeDetermineCompileFeatures.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Internal/FeatureTesting.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCXXCompiler.cmake.in"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeCXXCompiler.cmake"
}
],
"kind" : "cmakeFiles",
"paths" :
{
"build" : "/home/lucas/CLionProjects/tmp-policy/cmake-build-debug",
"source" : "/home/lucas/CLionProjects/tmp-policy"
},
"version" :
{
"major" : 1,
"minor" : 0
}
}

View File

@ -0,0 +1,171 @@
{
"inputs" :
[
{
"path" : "CMakeLists.txt"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeSystem.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeSystemSpecificInitialize.cmake"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeCCompiler.cmake"
},
{
"isGenerated" : true,
"path" : "cmake-build-debug/CMakeFiles/3.22.1/CMakeCXXCompiler.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeSystemSpecificInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeGenericSystem.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeInitializeConfigs.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/UnixPaths.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeFindCodeBlocks.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeExtraGeneratorDetermineCompilerMacrosAndIncludeDirs.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/ProcessorCount.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeLanguageInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-C.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/CMakeCommonCompilerMacros.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/GNU.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/CMakeCommonCompilerMacros.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-Clang-C.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU-C.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCommonLanguageInclude.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCXXInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeLanguageInformation.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Compiler/Clang.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-Clang-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU-CXX.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/Platform/Linux-GNU.cmake"
},
{
"isCMake" : true,
"isExternal" : true,
"path" : "/usr/share/cmake-3.22/Modules/CMakeCommonLanguageInclude.cmake"
}
],
"kind" : "cmakeFiles",
"paths" :
{
"build" : "/home/lucas/CLionProjects/tmp-policy/cmake-build-debug",
"source" : "/home/lucas/CLionProjects/tmp-policy"
},
"version" :
{
"major" : 1,
"minor" : 0
}
}

View File

@ -39,7 +39,7 @@
{ {
"directoryIndex" : 0, "directoryIndex" : 0,
"id" : "tmp_policy::@6890427a1f51a3e7e1df", "id" : "tmp_policy::@6890427a1f51a3e7e1df",
"jsonFile" : "target-tmp_policy-Debug-cda8d61ded076f2311ae.json", "jsonFile" : "target-tmp_policy-Debug-7c8af4715f6792deb793.json",
"name" : "tmp_policy", "name" : "tmp_policy",
"projectIndex" : 0 "projectIndex" : 0
} }

View File

@ -26,7 +26,7 @@
"objects" : "objects" :
[ [
{ {
"jsonFile" : "codemodel-v2-d0b91aea16fe9089df17.json", "jsonFile" : "codemodel-v2-d7cab6dcdb7f3013ba4d.json",
"kind" : "codemodel", "kind" : "codemodel",
"version" : "version" :
{ {
@ -35,7 +35,7 @@
} }
}, },
{ {
"jsonFile" : "cache-v2-4327d0d10f6390084c1d.json", "jsonFile" : "cache-v2-7057157c536c60dfd95c.json",
"kind" : "cache", "kind" : "cache",
"version" : "version" :
{ {
@ -44,7 +44,7 @@
} }
}, },
{ {
"jsonFile" : "cmakeFiles-v1-2d71857a96b31064ca46.json", "jsonFile" : "cmakeFiles-v1-54fa7c9382c2f5e70608.json",
"kind" : "cmakeFiles", "kind" : "cmakeFiles",
"version" : "version" :
{ {
@ -66,7 +66,7 @@
{ {
"cache-v2" : "cache-v2" :
{ {
"jsonFile" : "cache-v2-4327d0d10f6390084c1d.json", "jsonFile" : "cache-v2-7057157c536c60dfd95c.json",
"kind" : "cache", "kind" : "cache",
"version" : "version" :
{ {
@ -76,7 +76,7 @@
}, },
"cmakeFiles-v1" : "cmakeFiles-v1" :
{ {
"jsonFile" : "cmakeFiles-v1-2d71857a96b31064ca46.json", "jsonFile" : "cmakeFiles-v1-54fa7c9382c2f5e70608.json",
"kind" : "cmakeFiles", "kind" : "cmakeFiles",
"version" : "version" :
{ {
@ -86,7 +86,7 @@
}, },
"codemodel-v2" : "codemodel-v2" :
{ {
"jsonFile" : "codemodel-v2-d0b91aea16fe9089df17.json", "jsonFile" : "codemodel-v2-d7cab6dcdb7f3013ba4d.json",
"kind" : "codemodel", "kind" : "codemodel",
"version" : "version" :
{ {

View File

@ -36,6 +36,9 @@
[ [
{ {
"fragment" : "-g" "fragment" : "-g"
},
{
"fragment" : "-std=gnu++17"
} }
], ],
"language" : "CXX", "language" : "CXX",
@ -45,7 +48,7 @@
[ [
1 1
], ],
"standard" : "14" "standard" : "17"
}, },
"sourceIndexes" : "sourceIndexes" :
[ [
@ -90,7 +93,8 @@
"sourceIndexes" : "sourceIndexes" :
[ [
1, 1,
2 2,
3
] ]
} }
], ],
@ -111,6 +115,11 @@
"backtrace" : 1, "backtrace" : 1,
"path" : "policy_fundamentals.h", "path" : "policy_fundamentals.h",
"sourceGroupIndex" : 1 "sourceGroupIndex" : 1
},
{
"backtrace" : 1,
"path" : "accumulator.h",
"sourceGroupIndex" : 1
} }
], ],
"type" : "EXECUTABLE" "type" : "EXECUTABLE"

BIN
cmake-build-debug/tmp_policy Executable file

Binary file not shown.

View File

@ -85,6 +85,9 @@
<Unit filename="/home/lucas/CLionProjects/tmp-policy/accpolicy.h"> <Unit filename="/home/lucas/CLionProjects/tmp-policy/accpolicy.h">
<Option target="tmp_policy"/> <Option target="tmp_policy"/>
</Unit> </Unit>
<Unit filename="/home/lucas/CLionProjects/tmp-policy/accumulator.h">
<Option target="tmp_policy"/>
</Unit>
<Unit filename="/home/lucas/CLionProjects/tmp-policy/main.cpp"> <Unit filename="/home/lucas/CLionProjects/tmp-policy/main.cpp">
<Option target="tmp_policy"/> <Option target="tmp_policy"/>
</Unit> </Unit>

View File

@ -1,6 +1,28 @@
// tmp_policy
// Created by lucas on 22-7-26.
// Re-implementation of a typical policy architecture in C++ Template Meta-Programming.
#include <iostream> #include <iostream>
#include "accumulator.h"
#include <vector>
#include <string>
int main() { int main() {
std::cout << "Hello, World!" << std::endl; // Normal demo
std::vector<int> intVec;
intVec.reserve(10);
for (int i = 1; i <= 10; ++i)
intVec.push_back(i);
std::cout << Accumulator<PAdd, PAve, PResultTypeIs<int>>::eval(intVec) << std::endl;
std::cout << Accumulator<PAve, PAdd, PResultTypeIs<int>>::eval(intVec) << std::endl;
std::cout << Accumulator<PAdd, PNoAve, PResultTypeIs<int>>::eval(intVec) << std::endl;
std::cout << Accumulator<>::eval(intVec) << std::endl;
std::cout << Accumulator<PMul, PNoAve>::eval(intVec) << std::endl;
std::cout << Accumulator<PAve>::eval(intVec) << std::endl;
// Punchline (gusha)
std::vector<std::string> strVec;
for (int i = 1; i <= 10; ++i)
strVec.emplace_back("Today is KFC crazy Thursday V me ¥50\n");
std::cout << Accumulator<PAdd, PNoAve, PResultTypeIs<std::string>>::eval(strVec) << std::endl;
return 0; return 0;
} }

View File

@ -59,8 +59,8 @@ namespace NSPolicySelect {
}; };
// Template specialization of MajorFilter_. // Template specialization of MajorFilter_.
template <typename TEmptyContainer, typename TFirstPolicy, typename ... TOtherPolicies> template <typename TFirstPolicy, typename ... TOtherPolicies>
struct MajorFilter_<TEmptyContainer, struct MajorFilter_<PolicyContainer<>,
PolicyContainer<TFirstPolicy, TOtherPolicies...>> PolicyContainer<TFirstPolicy, TOtherPolicies...>>
{ {
// The beginning of the recursion. // The beginning of the recursion.
@ -112,27 +112,99 @@ namespace NSPolicySelect {
// For each policy object in the policy container, // For each policy object in the policy container,
// use MinorCheckInner_ to identify if there are another policy object // use MinorCheckInner_ to identify if there are another policy object
// having identical minor class. // having identical minor class.
// Also, the primitive template handles with the situation in which
// the policy container has no element.
template <typename TPolicyContainer> template <typename TPolicyContainer>
struct MinorCheckOuter_ struct MinorCheckOuter_
{ {
using type = std::true_type; using type = std::true_type;
}; };
// Template specialization of MinorCheckOuter_.
template <typename TCurPolicy, typename ... TRestPolicies> template <typename TCurPolicy, typename ... TRestPolicies>
struct MinorCheckOuter_<PolicyContainer<TCurPolicy, TRestPolicies...>> struct MinorCheckOuter_<PolicyContainer<TCurPolicy, TRestPolicies...>>
{ {
private: // The main logic of recursion.
using InnerResult_ = typename MinorCheckInner_<TCurPolicy, PolicyContainer<TRestPolicies...>>::type;
public:
using type = std::conditional_t< using type = std::conditional_t<
InnerResult_::value, // Does TCurPolicy and the rest policy objects have the same minor class?
MinorCheckInner_<TCurPolicy, PolicyContainer<TRestPolicies...>>::type::value,
// ... if no, proceed with next policy object in the policy container.
typename MinorCheckOuter_<PolicyContainer<TRestPolicies...>>::type, typename MinorCheckOuter_<PolicyContainer<TRestPolicies...>>::type,
// ... if yes, simply returns false and ends the recursion.
std::false_type std::false_type
>; >;
}; };
// Auxiliary template value meta-function definition: MinorCheck.
// Check if the TPolicyContainer has more than one element
// with the same minor class.
// If yes, returns false.
// If no, returns true.
template <typename TPolicyContainer> template <typename TPolicyContainer>
constexpr bool MinorCheck = MinorCheckOuter_<TPolicyContainer>::type::value; constexpr bool MinorCheck = MinorCheckOuter_<TPolicyContainer>::type::value;
// Template Declaration: template <typename> struct PolicySelectionResult.
// The template class which describes the policy selection result.
template <typename TPolicyContainer>
struct PolicySelectionResult;
// Template specialization of PolicySelectionResult.
// If the PolicyContainer only has one policy object in it,
// the PolicySelectionResult simply inherits from the policy object.
template <typename TPolicy>
struct PolicySelectionResult<PolicyContainer<TPolicy>> :
public TPolicy {};
// Template specialization of PolicySelectionResult.
// If the PolicyContainer has more than one policy object in it,
// the PolicySelectionResult inherits from the first policy object
// and the PolicySelectionResult of other policies.
// The result contains a definition that is dominant and unambiguous --
// each declaration comes from either Policy Group's initial definition
// or the policy object's overwritten definition.
template <typename TCurPolicy, typename ... TRestPolicies>
struct PolicySelectionResult<PolicyContainer<TCurPolicy, TRestPolicies...>> :
public TCurPolicy,
public PolicySelectionResult<PolicyContainer<TRestPolicies...>> {};
// Template Declaration: template <typename, typename> struct Selector_.
// The interface for users to get the policy selection result.
// TPolicyContainer - the policy container which contains the policy objects.
// TPolicyGroup - the original policy group.
template <typename TPolicyContainer, typename TPolicyGroup>
struct Selector_;
// Template specialization of Selector_.
// Restricts the TPolicyContainer can only be type PolicyContainer.
template <typename ... TPolicies, typename TPolicyGroup>
struct Selector_<PolicyContainer<TPolicies...>, TPolicyGroup>
{
// Use access specifier to prevent the users to use the internal types.
private:
// Use MajorFilter (MajorFilter_) to filter out the policy objects
// with unmatched MajorClass.
using FilteredPolicy = MajorFilter<PolicyContainer<TPolicies...>>;
// Check if the policy objects has conflict minor classes.
static_assert(MinorCheck<FilteredPolicy>, "Minor Class Set Conflict!");
public:
// Generate the policy selection result.
using type = std::conditional_t<
// Is the PolicyContainer empty?
IsArrayEmpty<FilteredPolicy>,
// ... if so, returns the policy group to represent the default definitions.
TPolicyGroup,
// ... if not, generate policy selection result to represent the user-selected definitions.
PolicySelectionResult<FilteredPolicy>
>;
};
// Auxiliary type definition - PolicySelect.
// To simplify the usage of Selector_.
template <typename TPolicyContainer, typename TPolicyGroup>
using PolicySelect = typename Selector_<TPolicyContainer, TPolicyGroup>::type;
} }
// Expose the NSPolicySelect::PolicySelect to global scope.
using NSPolicySelect::PolicySelect;
#endif //TMP_POLICY_POLICY_FUNDAMENTALS_H #endif //TMP_POLICY_POLICY_FUNDAMENTALS_H