[C++] 编译期间生成一个元素等差的std::initializer_list

发布于:2024-06-17 ⋅ 阅读:(12) ⋅ 点赞:(0)

前因

写编译器的时候需要一个常量英文字母表,懒得26个字母一个个打了,于是搓了个板子。

源代码

// c++14 required
#include <initializer_list>
#include <type_traits>

template <typename _Tp, _Tp first_elem, int item_number, typename = void, _Tp... args>
struct arithmetic_sequence {
    static constexpr std::initializer_list<_Tp> value = {args...};
};

template <typename _Tp, _Tp first_elem, int item_number, _Tp... args>
struct arithmetic_sequence<_Tp, first_elem, item_number, std::enable_if_t<sizeof... (args) < item_number>, args...> {
    static constexpr std::initializer_list<_Tp> value = arithmetic_sequence<_Tp, first_elem, item_number, void, args..., first_elem + sizeof... (args)>::value;
};

template <typename _Tp, _Tp first_elem, int item_number>
constexpr std::initializer_list<_Tp> arithmetic_sequence_v = arithmetic_sequence<_Tp, first_elem, item_number>::value;

示例

#include <set>

const std::set<char> lowercase_letter = arithmetic_sequence_v<arithmetic_sequence_v<char, 'a', 26>; // = {'a', 'b', 'c', ..., 'z'}

原理简述

众所周知的SFINAE (Substitution failure is not an error) 以及编译器在选择模板的优先顺序(偏特化>泛型),看代码应该不难懂,还有就是std::enable_if_tsizeof...需要稍微了解一下,公差这里是1,如果有需求可以再添加一个模板参数即可。

参考链接

std::enable_if_t
sizeof…