c++ - 模板方法特化+通用实现+优化=无限递归?
问题描述
我有以下生成文件来构建以下几个文件。
FLAGS = -O3
release: main Collection
g++ -o main Collection.o main.o $(FLAGS)
main: main.cpp
g++ -c main.cpp -std=c++17 $(FLAGS)
Collection: Collection.cpp Collection.hpp
g++ -c Collection.cpp -std=c++17 $(FLAGS)
clean: main
rm -f main *.o
/// Collection.hpp
#include <unordered_map>
struct RecallAsIs {
static constexpr int val = 0;
};
template <int value>
struct RecallAdd {
static constexpr int val = value;
};
class Collection {
public:
Collection();
~Collection();
void Add(int key, int value);
template <class RecallPolicy = RecallAsIs>
int Get(int key) const;
private:
std::unordered_map<int, int> values_;
};
template <class RecallPolicy>
int Collection::Get(int key) const {
return Get(key) + RecallPolicy::val;
}
/// Collection.cpp
#include "Collection.hpp"
Collection::Collection() = default;
Collection::~Collection() = default;
void Collection::Add(int key, int value) { values_[key] = value; }
template <>
int Collection::Get<RecallAsIs>(int key) const {
return values_.at(key);
}
/// main.cpp
#include <iostream>
#include "Collection.hpp"
int main() {
Collection c;
c.Add(10, 12);
std::cout << c.Get(10) << std::endl;
return 0;
}
关闭优化时,即。setting FLAGS = -O0
, 12 被打印到终端。但是,在设置时FLAGS = -O3
,程序最终挂起,我不太明白它为什么挂起。我最新的运行理论是,在Collection::Get
hpp 的一般实现中,编译器在启用优化并且看不到特化时内联,因此递归调用自身,导致程序挂起。我的分析正确吗?
解决方案
该程序格式错误,无需诊断。
[temp.expl.spec]/6如果模板、成员模板或类模板的成员被显式特化,则应在第一次使用该特化之前声明该特化,这将导致发生隐式实例化,在发生这种使用的每个翻译单元;不需要诊断...
推荐阅读
- vba - 如何根据文本输入将标志字段设置为是或否 - Microsoft-Project-VBA
- java - 具有构造函数的类的依赖注入,需要有关登录 SecurityContext 的用户的信息
- android - Expo 中的相机预览失真
- java - 乘法后获取最后两位数
- r - openxlsx 将单元格格式为带逗号的数字,并将 0 值替换为破折号
- java - 从外部类方法中清除图形
- vue.js - 在 Vue-Router 上替换路由时出现导航重复错误
- karate - 根据 SOAP 响应状态码 200 或 500 调用空手道功能文件
- c++ - 对象存在与对象生命周期不同吗?
- css - 为什么选择文本时相邻的 div 之间有垂直间隙?