c++ 具有非常量参数循环的模板

eyh26e7m  于 2023-05-08  发布在  其他
关注(0)|答案(1)|浏览(149)

在cpp中,你可以使用两个作弊代码来有效地对模板参数进行for循环,编译器将接受这些参数。如下所示。

#include <iostream>
#include <memory>

template<size_t k> void increment(size_t* v, size_t& i){ v[k]=i*i++; }

int main(){
    const size_t N = 10;
    size_t v[N], i=0;

    // for(size_t k=0;k<N;++k){ increment<k>(v,i); } // this would not work
    
    // so we write the following instead
    [v,i]<std::size_t... Is>(std::index_sequence<k...>){ // this line is the first cheat code
        (increment<k>(v,i), ...); // loop body
    }(std::make_index_sequence<N>{}); // this line is the second cheat code
    
    for(size_t k=0;k<N;++k){ std::cout << v[k] << " , "; }
}

问题:代码无法编译,因为在 * 循环体 * 行中,编译器要求v,i为常量。但正如示例所指出的,我不希望它们是常数。因此,我要求作弊代码,这使得它的工作。如果存在多个作弊码,我想要最短的。

5lhxktic

5lhxktic1#

mutable关键字可用于允许lambda表达式按值修改iT捕获的对象。
您还需要通过引用捕获v,否则increment将在v的副本上调用,并且没有可见的效果。
示例:https://godbolt.org/z/4xbPe4MdP

#include <iostream>
#include <memory>

template<size_t k> void increment(size_t* v, size_t& i){ v[k]=i*i++; }

int main(){
    constexpr std::size_t N = 10;
    std::size_t v[N];

    [&v,i = std::size_t{}]<std::size_t... k>(std::index_sequence<k...>) mutable
    {
        (increment<k>(v,i), ...);
    }(std::make_index_sequence<N>{});
    
    for(std::size_t k=0;k<N;++k){ std::cout << v[k] << " , "; }
}

相关问题