英文:
How to create std::initializer_list with integer_sequence?
问题
我有一个整数序列,并且需要为std::map
的构造函数创建std::initializer_list
。思路如下:
template<uint8_t... Indices>
static constexpr auto GenerateRegMap(std::integer_sequence<uint8_t, Indices...>)
-> std::initializer_list<std::pair<uint8_t const, uint8_t>>
{
return {{Indices, 0}...};
}
constexpr auto s = std::integer_sequence<uint8_t, 2, 4, 5, 7, 8, 10, 11, 13, 15>{};
std::map<uint8_t, uint8_t> m (GenerateRegMap(s));
std::cout << m.size() << std::endl;
for (const auto &pair : m)
{
std::cout << static_cast<int>(pair.first) << " has value " << static_cast<int>(pair.second) << std::endl;
}
在这里,std::initializer_list
通常是生成的,但不能返回它:它使用本地存储。我无法想象如何在原地编写GenerateRegMap
的内容。
实际上,m
是某个类的私有字段,并且最好在成员初始化列表中初始化它。
为什么我不从GenerateRegMap
中返回std::map<uint8_t, uint8_t>
?因为我遇到了一个错误:constexpr
函数不能具有非文字类型的返回类型。
英文:
I have an integer_sequence and I need to create std::initializer_list
for constructor of std::map
. The idea is below:
template<uint8_t... Indices>
static constexpr auto GenerateRegMap(std::integer_sequence<uint8_t, Indices...>)
-> std::initializer_list<std::pair<uint8_t const, uint8_t>>
{
return {{Indices, 0}...};
}
constexpr auto s = std::integer_sequence<uint8_t, 2, 4, 5, 7, 8, 10, 11, 13, 15>{};
std::map<uint8_t, uint8_t> m (GenerateRegMap(s));
std::cout << m.size() << std::endl;
for (const auto &pair : m)
{
std::cout << static_cast<int>(pair.first) << " has value " << static_cast<int>(pair.second) << std::endl;
}
There std::initializer_list
is normally generated, but it cannot be returned: it uses local storage. I cannot imagine how to write the content of GenerateRegMap
in place.
Really m
is private field of some class and it would be nice to init it in the member initializer list.
Why don't I return std::map<uint8_t, uint8_t>
from GenerateRegMap
? Because I've got an error: a constexpr function cannot have a nonliteral return type
.
答案1
得分: 2
不要回答我要翻译的问题。
以下是要翻译的内容:
"Instead of returning a local initializer_list
from the GenerateRegMap
, you can use C++14 variable template to generate the initializer_list
directly
template<uint8_t... Indices>
constexpr std::initializer_list<std::pair<uint8_t const, uint8_t>> my_list =
{{Indices, 0}...};
constexpr auto s = my_list<2, 4, 5, 7, 8, 10, 11, 13, 15>;
std::map<uint8_t, uint8_t> m(s);
If you want the variable template to take integer_sequence
as the template type, you can use template partial specialization to get values of integer_sequence
to initialize initializer_list
, for example
using L = std::initializer_list<std::pair<uint8_t const, uint8_t>>;
template<class Seq>
constexpr L my_list = {};
template<class Seq>
constexpr L my_list<const Seq> = my_list<Seq>;
template<uint8_t... Indices>
constexpr L my_list<std::integer_sequence<uint8_t, Indices...>> = {{Indices, 0}...};
This enables you to generate initializer_list
with pre-defined integer_sequence
constexpr auto s = std::integer_sequence<uint8_t, 2, 4, 5, 7, 8, 10, 11, 13, 15>{};
std::map<uint8_t, uint8_t> m(my_list<decltype(s)>);
"
英文:
Instead of returning a local initializer_list
from the GenerateRegMap
, you can use C++14 variable template to generate the initializer_list
directly
template<uint8_t... Indices>
constexpr std::initializer_list<std::pair<uint8_t const, uint8_t>> my_list =
{{Indices, 0}...};
constexpr auto s = my_list<2, 4, 5, 7, 8, 10, 11, 13, 15>;
std::map<uint8_t, uint8_t> m(s);
If you want the variable template to take integer_sequence
as the template type, you can use template partial specialization to get values of integer_sequence
to initialize initializer_list
, for example
using L = std::initializer_list<std::pair<uint8_t const, uint8_t>>;
template<class Seq>
constexpr L my_list = {};
template<class Seq>
constexpr L my_list<const Seq> = my_list<Seq>;
template<uint8_t... Indices>
constexpr L my_list<std::integer_sequence<uint8_t, Indices...>> = {{Indices, 0}...};
This enables you to generate initializer_list
with pre-defined integer_sequence
constexpr auto s = std::integer_sequence<uint8_t, 2, 4, 5, 7, 8, 10, 11, 13, 15>{};
std::map<uint8_t, uint8_t> m(my_list<decltype(s)>);
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论