C++ 浮点和双字面值模板类中的函数专门化
我试图找到一个解决方案,在模板类方法中包含常量数字文本。我正在制作一些数学模板类,用于float或double类型。问题在于,根据数据类型不同,文本是不同的(例如,“0.5f”表示浮点,而“0.5”表示双精度)。到目前为止,我提出了两个解决方案。第一个的一些假设代码:C++ 浮点和双字面值模板类中的函数专门化,c++,function,templates,literals,specialization,C++,Function,Templates,Literals,Specialization,我试图找到一个解决方案,在模板类方法中包含常量数字文本。我正在制作一些数学模板类,用于float或double类型。问题在于,根据数据类型不同,文本是不同的(例如,“0.5f”表示浮点,而“0.5”表示双精度)。到目前为止,我提出了两个解决方案。第一个的一些假设代码: 模板 上课 { 公众: T剂量测定法(tx); }; 模板 float SomeClass::doSomething(float x) { 浮动y=0.5f; /* *做计算。。。 */ 返回x; } 模板 double Some
模板
上课
{
公众:
T剂量测定法(tx);
};
模板
float SomeClass::doSomething(float x)
{
浮动y=0.5f;
/*
*做计算。。。
*/
返回x;
}
模板
double SomeClass::doSomething(双x)
{
双y=0.5;
/*
*做计算。。。
*/
返回x;
}
上面的方法强制重写它所使用的每种类型的整个方法
另一种方法:
模板
上课
{
公众:
T剂量测定法(tx);
私人:
T getValue();
};
模板
T SomeClass::doSomething(tx)
{
T y=getValue();
/*
*做计算。。。
*/
返回x;
}
模板
float SomeClass::getValue()
{
返回0.5f;
}
模板
double SomeClass::getValue()
{
返回0.5;
}
这个方法不需要为特定类型多次编写相同的方法,但需要为方法中需要使用的每个“幻数”都提供许多getValue()方法
有没有另一种“更优雅”的方法来解决这个问题?您不必担心这个问题-使用0.5,如果类型是float,编译器仍然会将其初始化为与使用0.5f时相同的最佳值 这有点冗长,但您可能想在这里通读我答案中的“支持多态性的其他机制”部分:
要在整个函数中更广泛地使用浮点常量,尤其是在比较和表达式中,请阅读下面提到的链接bluemess…假设实际上需要在两个专门化中使用不同的值(例如,0.5和0.5f不需要)这将大大减少打字工作量:
template <typename T>
class SomeClass
{
public:
T doSomething(T x);
private:
static const T magic_number_1;
};
template <typename T>
T SomeClass<T>::doSomething(T x)
{
T y = magic_number_1;
/*
* Do computations...
*/
return x;
}
template <>
const float SomeClass<float>::magic_number_1 = 0.5f;
template <>
const double SomeClass<double>::magic_number_1 = 0.5;
模板
上课
{
公众:
T剂量测定法(tx);
私人:
静态常数幻数1;
};
模板
T SomeClass::doSomething(tx)
{
T y=幻数1;
/*
*做计算。。。
*/
返回x;
}
模板
常量float SomeClass::magic_number_1=0.5f;
模板
常数double SomeClass::magic_number_1=0.5;
谢谢大家的回答和评论。我允许自己总结一下到目前为止所说的话,并补充我的结论
我将实现一些数学类模板,将其实例化以与float或double类型一起使用。需要在类内部使用一些数字文本。它们将是一些常用的数值文本和常量,如0.0、0.5、1.0、pi等。我正在寻找一种解决方案,使类实例化根据其类型在不同的文本上工作
是否使用浮点和双字面值?
关于是否需要为float和double使用单独的文本这个话题,讨论稍微深入了一点。这可能是因为我在问题中给出了一个不幸的例子。在本例中,文本将在编译时转换为正确的类型,因此不会造成任何伤害。但通常情况下,在表达式中需要使用文字,例如:
float foo(float x)
{
返回x*3.14;
}
这将迫使编译器将x转换为double,进行计算,然后将结果转换回float。这种行为的利弊:
优点:
- 精度提高,因为实际计算将以双倍速度进行 精确性
- 如果性能是一个问题,这可能会导致更快和更高的速度 执行速度较慢,具体取决于环境和平台。这 根据实现引入一些性能更改,这 就我所知,很糟糕
- 引入计算不一致性,因为某些操作将 根据文字使用情况,在浮点上完成,有些在双精度上完成。这 可能还会打开一些bug暴露
- 它打破了一开始将浮动类专门化的想法 因为不管怎样,内部计算都是在双精度上进行的
- 为每个模板实例化类型专门化方法,其中 必须使用文本。这可能是最糟糕的解决方案,因为它 强制编写同一代码两次,对 文字
- 使专用的
方法或作为专用的 成员。这可能会导致出现一些愚蠢的命名成员或方法 在类中,例如getValue()
getZeroPointFive()
- Mohammad和Tony Delroy指出,用
就可以了。转换为正确的类型将 必须在编译时完成static\u cast()