Ren*_*ene 6 c++ recursion templates definition
我有一个递归模板定义(我只是组成了这个术语).我认为代码更好地解释了它.
template<typename X>
class Domain
{
public:
X begin;
X end;
Domain(
X _begin,
X _end)
: begin(_begin)
, end(_end)
{
// ...
}
bool Contains(
const X& t) const
{
// ...
}
};
template<typename X, typename Y>
class IFunction
{
public:
Domain<X> myDomain;
public:
IFunction(
const Domain<X>& dom)
: myDomain(dom)
{
}
virtual Y
Calc(
const X& IV) const = 0;
virtual IFunction<X, Y>*
GetDerivative() const = 0;
};
template<typename X, typename Y, int n>
class NthOrderFunction
: public IFunction<X, Y>
{
public:
double coeffs[n+1];
public:
NthOrderFunction(
const Domain<X>& dom,
... )
: IFunction(dom)
{
}
virtual Y
Calc(
const X& IV) const
{
// temporary compile solution
return Y();
}
virtual IFunction<X, Y>*
GetDerivative() const
{
if ( n > 1 )
{
return new NthOrderFunction<X, Y, n-1>(dom, ...);
}
return new FlatLine<X, Y>(dom);
}
};
Run Code Online (Sandbox Code Playgroud)
我拿出了很多继承和其他关系来保持它的可读性,简单性和神秘性.因此,编辑代码时可能会遇到新的拼写错误,但请忽略它.代码已经运行了好几年,我唯一的问题就是我要指出的问题.
我最近添加了一个"GetDerivative"函数,它在NthOrderFunction类中的实现给了我一些问题.我知道模板类是在编译之前定义的,但是在预处理之后定义.因此,我无法看到如何使此功能工作.每个带模板参数n的NthOrderFunction都需要带模板参数n-1的NthOrderFunction.你可以看到这是一个问题.问题是,即使n在使用中永远不会是负数,但我没有做任何编码,也会说服"模板定义引擎"不打扰n <1的实例;
有没有人遇到任何问题?你提出了什么解决方案?
这与模板元编程101示例 - 阶乘相同,只是内容稍微复杂一些.
template<int N> struct factorial { enum { value = N * factorial<N-1>::value }; };
Run Code Online (Sandbox Code Playgroud)
而且你需要相同的解决方案 - 基础案例的专业化.
template<> struct factorial<1> { enum { value = 1 }; };
Run Code Online (Sandbox Code Playgroud)
你的是部分的而不是满的,但它仍然有效.
添加如下内容:
template<typename X, typename Y>
class NthOrderFunction<X, Y, 1>
: public IFunction<X, Y>
{
public:
double coeffs[n+1];
public:
NthOrderFunction(
const Domain<X>& dom,
... )
: IFunction(dom)
{
}
virtual Y
Calc(
const X& IV) const
{
// temporary compile solution
return Y();
}
virtual IFunction<X, Y>*
GetDerivative() const
{
return new FlatLine<X, Y>(dom);
}
};
Run Code Online (Sandbox Code Playgroud)
并从递归案例中删除 n==1 案例。
作为建议,获取一些有关模板元编程的书籍或教程等。基本技术之一是以这种方式在模板中使用递归。严格来说,这还不是元编程,它只是递归模板。这本书/教程将解释更高级的技巧是如何工作的,您可以在扩展此内容时使用它们来获益。
这样做的原因是,原始版本仍然会将编译时“if”扩展为运行时代码(永远不会被执行)。该代码用不存在的情况替换了可以编译出来的一种情况,因此没有无限递归的选项。