std::vector
或不是的话,它允许我分支到不同的专业化。某种
is_base_of
用于模板。有这样的事吗?
#include <type_traits>
#include <iostream>
#include <vector>
#include <list>
template<typename Test, template<typename...> class Ref>
struct is_specialization : std::false_type {};
template<template<typename...> class Ref, typename... Args>
struct is_specialization<Ref<Args...>, Ref>: std::true_type {};
int main()
{
typedef std::vector<int> vec;
typedef int not_vec;
std::cout << is_specialization<vec, std::vector>::value << is_specialization<not_vec, std::vector>::value;
typedef std::list<int> lst;
typedef int not_lst;
std::cout << is_specialization<lst, std::list>::value << is_specialization<not_lst, std::list>::value;
}
std::vector
的专业化:
#include <type_traits>
#include <iostream>
#include <vector>
template<typename>
struct is_std_vector : std::false_type {};
template<typename T, typename A>
struct is_std_vector<std::vector<T,A>> : std::true_type {};
int main()
{
typedef std::vector<int> vec;
typedef int not_vec;
std::cout << is_std_vector<vec>::value << is_std_vector<not_vec>::value;
}
std::vector<T>
的模板函数进行重载。在这种情况下,编译器将选择最专业的模板。
template<class T>
bool is_vector(const std::vector<T>& x) {return true;}
template<class T>
bool is_vector(const T& x) {return false;}
示例:
auto x {std::vector<double> {23, 32, 33}};
auto y {1.2};
std::cout << is_vector(x) << std::endl;
std::cout << is_vector(y) << std::endl;
std::vector<std::vector<float>>
是否是
std::vector<WHATEVER>
的一种。所以我实现了一个通用的
is_fuzzy_type_match_v
来检查它们,通过使用这个
consteval
函数,你可以在任何类型的模板中完成它,甚至是可变参数模板。这里是代码:
#include <type_traits>
namespace noaland {
struct i_dont_care {};
template<typename T>
struct is_i_dont_care : std::false_type {};
template<>
struct is_i_dont_care<i_dont_care> : std::true_type {};
// if two type are not the same
template<typename X, typename Y>
struct is_fuzzy_type_matched {
consteval auto operator()() {
if constexpr (noaland::is_i_dont_care<X>::value || noaland::is_i_dont_care<Y>::value || std::is_same_v<X, Y>) {
return std::true_type{};
} else {
return std::false_type{};
}
}
};
template<typename X, typename Y>
inline constexpr auto is_fuzzy_type_matched_v = decltype(is_fuzzy_type_matched<X, Y>()())::value;
template<bool... R>
consteval bool conjunction() {
return (R && ...);
}
template<template<typename...> typename X, template<typename...> typename Y, typename... SUB_X, typename... SUB_Y>
struct is_fuzzy_type_matched<X<SUB_X...>, Y<SUB_Y...>> {
consteval auto operator()() {
if constexpr (!conjunction<is_fuzzy_type_matched_v<SUB_X, SUB_Y>...>()) {
return std::false_type{};
} else {
return std::true_type{};
}
}
};
}
您可以像这样使用此功能:
int main() {
static_assert(noaland::is_fuzzy_type_matched_v<std::vector<std::vector<std::vector<int>>>, std::vector<noaland::i_dont_care>>);
return 0;
}
由于我使用的是 C++20 功能 consteval
,因此您需要添加
--std=c++20
,或者您可以将
consteval
更改为
constexpr
。