首页 > 解决方案 > 对不同大小的 N 个数组的每个元素应用相同的函数

问题描述

让我们考虑一个实现A了构造函数和成员函数的类foo

这是一些代码:

constexpr int size1 = 100;
constexpr int size2 = 13;
constexpr int size3 = 48;
constexpr int size4 = 231;
constexpr int size5 = 5;
constexpr int size6 = 125;
constexpr int size7 = 88;
constexpr int size8 = 549;
constexpr int size9 = 417;

int main(void)
{
    std::array<A*, size1> array1;
    std::array<A*, size2> array2;
    std::array<A*, size3> array3;
    std::array<A*, size4> array4;
    std::array<A*, size5> array5;
    std::array<A*, size6> array6;
    std::array<A*, size7> array7;
    std::array<A*, size8> array8;
    std::array<A*, size9> array9;

    // Solution

    return 0;
}

我想构造每个数组的每个元素,然后为每个元素调用成员函数foo

基本上,我想做:

for (auto& element : array1)
{
    element = new A();
    element->foo();
}

对于每个数组。

在不连续写下九个 for 循环的情况下,最短和最简单的方法是什么?

标签: c++arraysfor-loopc++17

解决方案


您很可能希望将代码打包到特定的初始化函数中。但是,由于 ( std::) 不同长度的数组实际上是不同的类型,您要么需要模板函数,要么需要对数组的内部原始数组 ( data()) 进行操作:

template <typename T>
void initialize(T& t)
{
    for(auto& a : t)
    //      ^ reference to pointer (!)
    {
        a = new A();
        a->foo();
    }
    std::cout << std::endl;
}

然后,您只需在每个数组上调用此函数。如果这还不够短,您可以将其打包到可变参数模板函数中:

template <typename T, typename ... TT>
void initialize(T& t, TT& ... tt)
{
    initialize(t);
    initialize(tt...);
}

// alternatively, a bit shorter, with C++17 fold expression:
template <typename ... TT>
void initialize(TT& ... tt)
{
    (initialize(tt), ...);
}

在呼叫点,这很可能是你能得到的最短的(除了选择一个更短的名字):

initialize(array1, array2, array3, array4, ...);

推荐阅读