我發現自己想要/需要使用一個變體復合型別作為模板引數。不幸的是,std::tuple<>不是一個結構型別,這使得明顯的方法是不可行的:
#include <tuple>
template<typename。Ts>
struct composite {
std::tuple<Ts...> 運算元。
};
template<auto v>
void foo(){}。
int main() {}。
constexpr composite tmp{std::make_tuple(1,2, 3)};
foo<tmp>(); // <----- Nope!
}
是否有一種合理的方式來構建這樣的復合體,并將其作為一種結構型別來使用?
既然單獨的 MCVE 是可以通過 "只需讓 foo() 成為一個變數模板 "來解決的,這里有一個更具代表性的例子:
#include <concepts>/span>
#include <tuple>
template <typename T, template <typename ...> typename U>
concept TemplatedConfig = requires(T x) {
{ U(x) } -> std::same_as<T> 。
//A few more things identifying T as a valid config。
};
template<auto Config>
struct proc;
//Basic
struct Basic {};
template< Basic v>
struct proc<v> {
constexpr int foo(){ return 0; }
};
//注解
template<typename T>
struct Annotated {
T v;
int annotation;
};
template<TemplatedConfig<Annotated> auto v>
struct proc<v> {
constexpr int foo(){ return 1; }
};
//...更多的配置/專業對...
// Composite
template<typename ... 零件>。
struct Composite {
std::tuple<Parts...> parts。
};
template<TemplatedConfig<Composite> auto v>
struct proc<v> {
constexpr int foo(){ return 2; }
};
int main() {
constexpr Basic a = Basic{};
constexpr 注釋的b{a, 12}。
constexpr 復合c{std::make_tuple(a, b)};
static_assert(proc<a>{}.foo() == 0) 。
static_assert(proc<b>{}.foo() == 1) 。
static_assert(proc<c>{}.foo() == 2); <----- : (
}
編輯:如果有人好奇基于公認答案的(幾乎)完全實作的元組類是什么樣子。https://gcc.godbolt.org/z/ThaGjbo67
uj5u.com熱心網友回復:
創建你自己的類似結構元組的類? 類似于:
template <std::size_t I, typename T>
struct tuple_leaf
{
T資料。
};
template <typename T> struct tag{ using type = T; };
template <typename Seq, typename...>
struct tuple_impl;
template <std::size_t ... Is, typename...。Ts>。
struct tuple_impl<std::index_sequence<Is...>, Ts...> : tuple_leaf<Is, Ts> ...
{
constexpr tuple_impl(Ts... args) : tuple_leaf<Is, Ts> {args}... {}
};
template <typename T, std:: size_t I> constexpr const T&。get(const tuple_leaf<I, T>& t) { return t. data; }
template <typename T, std:: size_t I> constexpr T& get(tuple_leaf<I, T>& t){ return t. data; }
template <std:: size_t I, typename T> constexpr const T&。get(const tuple_leaf<I, T>& t) { return t. data; }
template <std:: size_t I, typename T> constexpr T& get(tuple_leaf<I, T>& t){ return t. data; }
template <std::size_t I, typename T>
tag<T> tuple_element_tag(const tuple_leaf<I, T> & )。
template <std::size_t I, typenameTuple>
using tuple_element = decltype(tuple_element_tag<I>(std::declval<Tuple>() )。
template<std::size_t I, typenameTuple>
using tuple_element_t = typename tuple_element<I, Tuple> :type;
template <typename ...。Ts>
using tuple = tuple_impl<std::make_index_sequence<sizeof...(Ts)>, Ts...>;
轉載請註明出處,本文鏈接:https://www.uj5u.com/qiye/306754.html
標籤:
下一篇:獲取所有運行行程的名稱串列
