[英]Function parameter with unknown value cannot be used in a constant expression
Why I get compilation error "function parameter 'field' with unknown value cannot be used in a constant expression"?为什么会出现编译错误“无法在常量表达式中使用具有未知值的函数参数‘字段’”?
All marked as constexpr, I don't see any problems with knowing value at compile time.全部标记为 constexpr,我认为在编译时知道值没有任何问题。
Is there any way to fix this error?有没有办法解决这个错误?
#include <tuple>
#include <string_view>
namespace {
template<typename Tuple, typename F, std::size_t... Indices>
constexpr void for_each_impl(Tuple &&tuple, F &&f, std::index_sequence<Indices...>) {
(f(std::get<Indices>(std::forward<Tuple>(tuple))), ...);
}
template<typename Tuple, typename F>
constexpr void for_each(Tuple &&tuple, F &&f) {
const auto N = std::tuple_size<std::remove_reference_t<Tuple>>::value;
for_each_impl(std::forward<Tuple>(tuple), std::forward<F>(f), std::make_index_sequence<N>{});
}
template <typename T, typename... Tuple>
constexpr auto has_type(const std::tuple<Tuple...> &tuple) {
return std::disjunction_v<std::is_same<T, Tuple>...>;
}
}// namespace
template<typename A>
struct meta_field {
constexpr meta_field(std::string_view name, A attributes)
: name(name), attributes(attributes) {
}
const std::string_view name;
const A attributes;
};
int main() {
constexpr auto fields = std::make_tuple(meta_field("a121213", std::make_tuple(int(5))), meta_field("hello", std::make_tuple()));
for_each(fields, [](const auto &field) {
// why unknown value?
if constexpr (has_type<int>(field.attributes)) {
}
});
}
function parameter are not constexpr, so you have to play with type instead: function 参数不是 constexpr,所以你必须使用 type 来代替:
template <typename T, typename Tuple> struct has_type : std::false_type {};
template <typename T, typename... Ts> struct has_type<T, std::tuple<Ts...>> : std::disjunction<std::is_same<T, Ts>...> {};
with usage similar to用法类似于
for_each(fields, [](const auto &field) {
if constexpr (has_type<int, std::decay_t<decltype(field.attributes)>>::value) {
std::cout << std::get<int>(field.attributes) << std::endl;
}
});
attributes
is not constexpr
. attributes
不是constexpr
。
You could make it a template parameter and make it static constexpr
in the class.您可以将其设为模板参数并在 class 中将其
static constexpr
。 Though, for non-type template arguments to be floating point values, you need C++20.虽然,对于非类型模板 arguments 是浮点值,您需要 C++20。
template<auto... Attributes>
struct meta_field {
constexpr meta_field(std::string_view name)
: name(name) {
}
static constexpr std::tuple<decltype(Attributes)...> attributes{Attributes...};
const std::string_view name;
};
// ...
constexpr auto fields = std::make_tuple(
meta_field<5>("a121213"),
meta_field<>("hello"));
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.