循环 typedef 列表

Loop a list of typedefs

本文关键字:列表 typedef 循环      更新时间:2023-10-16

如果标题有点误导,我很抱歉。

我有一个循环一些数据的函数。此数据的类型因每次迭代而更改。

基本上我有这样的东西:

for(int i = 0; i < limit; i++)
{
type object;
object.do_stuff();
}
例如,在第一次迭代中,"type">

将是int,在第二次迭代中,"type"将是双精度,依此类推。

我不能使用varyadic模板,因为我有100多个元素,据我所知,这对系统来说将是非常繁重的。

我的想法是创建一个"typedefs向量"来循环所有类型的对象。

vector<????> type;
type.push_back(int);
type.push_back(double);
...
for(int i = 0; i < limit; i++)
{
type[i] object;
object.do_stuff();
}

我不知道这是否遥不可及。

我看到了排版表的基础知识,但我不知道是否可以重现循环。

我不能使用varyadic模板,因为我有100多个元素,据我所知,这对系统来说会非常费力。

您所知道的要么过时,要么不准确。只需查看 metaben.ch,即可了解排字列表可以在最小的编译时间影响下获得多大。


我的想法是创建一个"typedefs向量"来循环所有类型的对象。

这是一个打字表。以下是您可以执行的操作:

// Store the type in a value for convenience
template <typename T>
struct type_wrapper
{
using type = T;
};
template <typename... Ts>
struct typelist
{
template <typename F>
constexpr void for_each(F&& f)
{
// C++17 fold expression over comma operator
(f(type_wrapper<Ts>{}), ...);
}
};

C++17 用法:

typelist<int, float, char>{}.for_each([](auto t)
{
using type = typename decltype(t)::type;
// Use `type`
});

C++20 用法(对typelist略有改动):

template <typename... Ts>
struct typelist
{
template <typename F>
constexpr void for_each(F&& f)
{
// C++17 fold expression over comma operator
(f.template operator()<Ts>(), ...);
}
};
typelist<int, float, char>{}.for_each([]<typename T>()
{
// Use `T`
});

我写了一篇与此主题相关的短文:"使用 C++20 lambda 进行编译时迭代 ">.

我们可以用稍微不同的方式看待这个问题,并说你可能真正想要的是要做的事情的向量(或者,我可能更愿意说,列表),这可以通过<功能>中的一些工具以非常通用的方式实现。 一起来看看:

#include <vector>
#include <functional>
#include <iostream>
static void process_int (int i) { std::cout << "process_int " << i << "n"; }
static void process_string (std::string s) { std::cout << "process_string " << s << "n"; }
// ...                                            
int main()
{
std::vector <std::function <void ()>> v;
v.push_back (std::bind (process_int, 42));
v.push_back (std::bind (process_string, "Hello world"));
for (auto f : v)
f ();                    
}

输出:

process_int 42
process_string Hello world

它再简单不过了,你可以用各种聪明(或不那么聪明)的方式来适应你的特定用例。 正如现场演示所示,在 C++11 中应该没问题。 您也可以将 lambda 传递给std::bind

现场演示。