constexpr上下文中std::initializer_list的验证
Validation of an std::initializer_list in constexpr context
我有一些类,希望在编译时由需要某种级别验证的初始值设定项列表初始化。
我第一次尝试static_assert,但编译时不会出现错误"静态断言的非恒定条件">
导致生成错误的最佳方法是什么?
class foo {
public:
constexpr foo(std::initializer_list<bar> items) {
for(auto &&i: items) {
if(i == 12) // example validation logic
// fail the build
}
}
}
constexpr foo foo_list({0,1,2,3,4,5});// should succeed
constexpr foo foo_list_bad({0,1,12,4,68});// should fail to build
使用编译时不能使用的构造,例如异常:
constexpr foo(std::initializer_list<bar> items)
{
for (auto&& i : items) {
if (i == 12) {
throw std::invalid_argument{""}; // for example
}
}
}
如果异常被禁用,则为错误断言:
constexpr foo(std::initializer_list<bar> items)
{
for (auto&& i : items) {
assert(i != 12);
}
}
或者如果定义了NDEBUG
,则调用运行时函数:
constexpr foo(std::initializer_list<bar> items)
{
for (auto&& i : items) {
if (i == 12) {
std::cerr << "Errorn";
}
}
}
如果仅运行时表达式作为常量表达式求值的一部分进行求值,则需要进行诊断。
static_assert
不起作用,因为它的自变量必须是常量表达式,而constexpr
函数的自变量则不是。
相关文章:
- 使用std::multimap迭代器创建std::list
- 来自 std::list 的迭代器 .end() 按预期返回"0xcdcdcdcdcdcdcdcd"但 .begin()
- 正在尝试了解输入验证循环
- 如何在 C 中正确使用 libiconv 使其不会报告"Arg list too long"?
- C++中带有List类的迭代器Segfault
- 使用"std::unordereded_map"映射到"std::list"对象
- 如何在C++中检查2D数组中负值的输入验证
- GCC对可能有效的代码抛出init list生存期警告
- 使用std::list创建循环链表
- LibGit2 SSH身份验证失败
- Vulkan验证层不断在VkQueuePresentKHR()上抛出图像布局错误
- 重载Singly Linked List中的赋值运算符
- constexpr上下文中std::initializer_list的验证
- 正在验证c++中用户的整数输入
- 加密++验证大文件签名
- C++卡验证问题
- 验证指针链
- '[](std::list& list)<int>{return std::move(list)}(list)' 是否保证将 'list' 留空?
- 如果 KEY 是 std::list 或 std::vector 而不是值,那么 std::map 的默认行为是什么?
- 为什么这个 std::queue/指向结构的指针列表直到 List.Size() == 0 才释放内存?