c++ - 在 C++ 中进行 N 阶乘编译时间的 3 种不同/相同方法
问题描述
我正在尝试使用模板元编程、constexpr 和 if constexpr,并提出了 3 种不同的方法来进行 N 递归/N 阶乘运算。
所有三个示例都是我在 SO 上或通过在网上搜索找到的 - 然后对其进行了修改,所以它们也是一样的
第一个示例是使用模板元编程:示例 1
template<int N>
struct NGenerator
{
static const int result = N + NGenerator<N-1>::result;
};
template<>
struct NGenerator<0>
{
static const int result = 1;
};
static int example1 = NGenerator<5>::result;
第二个仍在使用模板,但我在示例 2中抛出了一个 constexpr
template<int N>
constexpr int example2()
{
return N + example2<N - 1>();
}
template<>
constexpr int example2<0>()
{
return 1;
}
static int ex2 = example2<5>();
第三个,是我删除模板并“仅”使用 constexpr 的地方:示例 3
constexpr int generator(int n)
{
return (n <= 1) ? 1 : n + generator(n - 1);
}
static int ex3 = generator(5);
在我看来,所有三个都做同样的事情 - 当输入数字是编译时间常数时。这三个都是递归的,所有三个都在编译时工作。
我的问题是——这三者有什么区别?哪一个最可取?
最后——我想实现“if constexpr”但没能实现,所以我的解决方法是在示例 3 中执行“if 语句”——这并不是真正的 if 语句,但是如果 - 如果它以任何方式相同,我可以得到最接近编译时间,我不确定。
解决方案
像这样的玩具例子不会有太大的不同。对于更复杂的示例,递归模板实例化实际上具有与所有模板实例化名称(包括参数)的长度之和成正比的内存成本。这真的很容易炸。
根据我的经验constexpr
,函数往往编译得更快。
编译器可能会记住所有 3 个;但是 constexpr 非模板函数会喷出更少的符号(噪音)。
比所有这些更好的是带有循环的 constexpr 函数。
编译器可以在运行时自由地执行大多数选项,因为您不坚持编译时评估。替换static int
为constexpr int
。
推荐阅读
- flutter - Flutter VsCode 错误:您没有用于调试 YAML 的扩展
- kie - 如何使用 kie 服务器的 docker 镜像创建新容器?
- java - 如何重用多个 DTO(spring boot)
- python - 访问 CSV 文件中名称 X 的最新条目
- reactjs - ReactJs can't fix missing semicolon error before "render()"
- sulu - SULU Admin 上的摘录和分类法
- ios - Flutter Charts:添加库不会让我在应用程序中更改颜色。我能做些什么?
- javascript - 更新组件值时 UseContext 不会重新渲染
- tensorflow - Keras 输入不兼容
- flutter - Flutter:如何在 Flutter 中创建这种旋转图标动画?