编译C ++循环的时间评估 [英] Compile time evaluation of a C++ loop

查看:98
本文介绍了编译C ++循环的时间评估的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想写一个C ++循环,我想在编译时评估。这是因为我需要使用循环变量作为模板参数来初始化一个类。在非常简单的情况下,它看起来像:

I am trying to write a C++ loop that I want evaluated at compile-time. This is because I need to use the looping variable as a template argument to initialize a class. In the very simple case it would look something like:

for (unsigned int i = 1; i < 8; i++) {
  Vector<i> foo;
  // do something with foo
}

经过一些类似的StackOverflow 问题,我发现了一种递归编写静态循环的方法。现在我的代码看起来像这样:

After going through some similar StackOverflow questions, I found a way to write a static for loop recursively. Now my code looks something like this:

template <unsigned int i, unsigned int end>
struct static_for {
  template <typename Lambda>
  void operator()(const Lambda& function) const {
    if (i < end) {
      function(i);
      static_for<start + 1, end>(function);
    }
  }
};

template <int N>
struct static_for<N, N> {
  template <typename Lambda>
  void operator()(const Lambda& function) const {
    // This is just to avoid the unused variable warning - does nothing.
    (void)function;
  }
};

这是完美的,如预期。为了调用 static_for 循环,我可以简单地写:

This works perfectly and as expected. In order to call this static_for loop I can simply write:

static_for<0, 8>()([](int size) {
      // some code here.
    });

但是,问题是我还是不能评价 i 在编译时。由于在我无法在lambda表达式中创建模板对象:

The problem, however, is that I can still not evaluate i at compile time. As in I cannot create a templated object within the lambda expression:

static_for<0, 8>()([](int size) {
      Vector<size> var; // does not compile as size is not a constexpr.
    });

如何使这项工作?我的 static_for 循环有 i 变量作为模板参数,在编译时可用。我希望我的lambda表达式在编译时接收这个参数( size ),而不是作为运行时变量传递。这将如何工作?

How can I make this work? My static_for loop has the i variable as a template argument which is available to it at compile time. I would like my lambda expression to receive this argument (size) also at compile time rather than being passed in as a runtime variable. How would this work? Conceptually this seems simple and useful as a more general language feature as well.

推荐答案

如果你可以使用C ++ 14,可以将 std :: integral_constant 传递给通用lambda,而不是 int gcc.godbolt.org示例

If you can use C++14, you could pass an std::integral_constant to a generic lambda instead of an int. gcc.godbolt.org example

template <unsigned int i, unsigned int end>
struct static_for {
  template <typename Lambda>
  void operator()(const Lambda& function) const {
    if (i < end) {
      function(std::integral_constant<int, i>{});
      static_for<start + 1, end>(function);
    }
  }
};

static_for<0, 8>()([](auto size) {
  Vector<decltype(size)::value> var; // does not compile as size is not a constexpr.
});

这篇关于编译C ++循环的时间评估的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆