Comment par un type de variante donné
using V = std::variant<bool, char, std::string, int, float, double, std::vector<int>>;
déclarer deux types de variantes
using V1 = std::variant<bool, char, int, float, double>;
using V2 = std::variant<std::string, std::vector<int>>;
d'où V1
inclut tous les types arithmétiques V
et V2
inclut tous les types non arithmétiques V
?
V
peut être un paramètre d'une classe de modèle, par exemple:
template <class V>
struct TheAnswer
{
using V1 = ?;
using V2 = ?;
};
en général, les critères peuvent être une constexpr
variable comme celle-ci:
template <class T>
constexpr bool filter;
c++
c++17
std-variant
Alexey Starinsky
la source
la source
Types...
intérieurstd::variant
directement, comme ça ?std::variant
est mal formé.std::variant<>
est mal formée, donc je suis clair. Je tweak pour queV1
etV2
retomber àstd::variant<std::monostate>
bien.Avec Boost.Mp11 , il s'agit d'un court one-liner (comme toujours):
Vous pouvez aussi utiliser:
pour rendre les deux plus symétriques.
Alternativement,
la source
mp_filter
Sur quelles idées est-ce basé?EDIT Étant donné qu'une variante vide (
std::variant<>
) est mal formée (selon cppreference ) et qu'elle devrait être utilisée à lastd::variant<std::monostate>
place, j'ai modifié la réponse (ajouté unetuple2variant()
spécialisation pour le tuple vide) pour prendre en charge le cas lorsque la liste des types pourV1
ouV2
est vide.C'est un petit
decltype()
délire mais ... si vous déclarez un couple de filtres auxiliaires de fonction comme suitet un tuple à la fonction variant (avec une spécialisation pour les tuples vides, pour éviter un vide
std::variant
)votre classe devient simplement (?)
Si vous voulez quelque chose de plus générique (si vous voulez passer
std::arithmetic
comme paramètre de modèle), vous pouvez modifier lafilterArithm()
fonction en passant un paramètre de filtre modèle-modèleF
(renomméfilterType()
)La
TheAnswer
classe devientet la
TA
déclaration prend égalementstd::is_arithmetic
Ce qui suit est un exemple de compilation complet avec
std::is_arithmetic
comme paramètre et unV2
cas videla source
void
.void
, pour autant que je sache, est interdit comme type dans unstd::variant
.std::variant<void>
est mal formé, mais il semble que cestd::variant<>
soit OK si sa définition n'est pas instanciée .