我对此进行了大量研究,但未能找到解决该问题的设计模式。这是对我要执行的操作的最简单描述。
#include <iostream>
using namespace std;
template <class T, T default_value=T{}>
class A{
private:
T inclassValue;
public:
A(T icv):inclassValue{icv}{}
const T& operator[](int k){
if(k==1) return inclassValue;
return default_value;
}
};
struct two_int{int x;int y;};
int main(){
A<int> a{4};
cout << "a[0]=" << a[0] << endl;
cout << "a[1]=" << a[1] << endl;
/*
A<two_int> b{{3,5}};
cout << "b[0]=" << b[0].x << "," << b[0].y << endl;
cout << "b[1]=" << b[1].x << "," << b[1].y << endl;
*/
return 0;
}
代码将按预期编译、链接和输出
a[0]=0
a[1]=4
编译器会提示并针对使用 default_value 的代码行发出警告
return default_value;//Returning reference to local temporary object
这有点道理。取消注释 main 中的最后一部分并进行编译,这次编译器在构建模板时发出错误
template <class T, const T default_value= T{}>//A non-type template parameter cannot have type 'two_int'
虽然我理想中希望的是
b[0]=0,0
b[1]=3,5
我能够通过添加一个额外的辅助类来提出解决方案,该辅助类将为模板参数提供 T 的默认值(作为静态成员)。我不相信我的技巧的稳健性,我想知道是否存在解决这个问题的设计模式。类型警告和非类型错误。另外,我要补充一点,我的主要目标是能够随意提供 default_value(例如 int 为 6 而不是 0)。
谢谢
最佳答案
不确定您在寻找什么,但也许用于创建静态默认 T 的静态助手可能有用:
template <typename T>
static const T& default_value() {
static const T* t = new T{};
return *t;
}
请注意,即使跨线程(在 c++11 中),这也将最多构造 T 一次,但仍然永远不会破坏 T。由于它是静态的,因此缺少破坏可能是可以接受的,但这当然取决于 T。
关于c++ - 如何返回对非类型模板参数的默认值的引用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48307977/