如何理解C++;模板 我用C++模板编写了偶数/奇数的判断代码。 #include <iostream> template <int N, int Mod2=N%2> struct Print { Print() { std::cout << N << std::endl; } }; template <int N> struct Print<N, 0> { Print() { std::cout << "Even!" << std::endl; } }; template <int N> struct Print<N, 1> { Print() { std::cout << "Odd!" << std::endl; } }; template <int N> struct EvenOdd { EvenOdd() { EvenOdd<N+1>(); Print<N>(); } }; template <> struct EvenOdd<10> { EvenOdd() { std::cout << "Hey!" << std::endl; } }; int main() { EvenOdd<0>(); return 0; }
我预测EvenOdd::EvenOdd()/=>“Hey!”最后会被调用。但是,这是错误的 EvenOdd<10>::EvenOdd() //=> "Hey!"如何理解C++;模板 我用C++模板编写了偶数/奇数的判断代码。 #include <iostream> template <int N, int Mod2=N%2> struct Print { Print() { std::cout << N << std::endl; } }; template <int N> struct Print<N, 0> { Print() { std::cout << "Even!" << std::endl; } }; template <int N> struct Print<N, 1> { Print() { std::cout << "Odd!" << std::endl; } }; template <int N> struct EvenOdd { EvenOdd() { EvenOdd<N+1>(); Print<N>(); } }; template <> struct EvenOdd<10> { EvenOdd() { std::cout << "Hey!" << std::endl; } }; int main() { EvenOdd<0>(); return 0; },c++,templates,C++,Templates,我预测EvenOdd::EvenOdd()/=>“Hey!”最后会被调用。但是,这是错误的 EvenOdd<10>::EvenOdd() //=> "Hey!" 为什么“嘿!”首先输出?您的模板EvenOdd仅显式专用于参数10,所有其他专用化的构造函数都会为模板参数N+1实例化一个匿名EvenOdd,作为其构造函数中的第一个操作 这意味着在任何EvenOdd对象构造Print对象之前,EvenOdd构造函数将递归生成匿名EvenOdd临时对象,直到模板参数10 构造第11个EvenOdd
为什么“嘿!”首先输出?您的模板
EvenOdd
仅显式专用于参数10
,所有其他专用化的构造函数都会为模板参数N+1
实例化一个匿名EvenOdd
,作为其构造函数中的第一个操作
这意味着在任何EvenOdd
对象构造Print
对象之前,EvenOdd
构造函数将递归生成匿名EvenOdd
临时对象,直到模板参数10
构造第11个
EvenOdd
对象会输出“嘿!”,然后构造第一个Print
对象。此行为与模板无关。这是基本的递归。在打印之前,可以递归地实例化EvenOdd
。因此,打印任何内容的第一个实例是最里面的,也就是EvenOdd
事情是这样的:EvenOdd
做的第一件事就是实例化EvenOdd
。只有在完成后,才会调用Print
。直到EvenOdd
完成实例化EvenOdd
并打印,这一过程才会完成,依此类推:
EvenOdd<0>
EvenOdd<1>
EvenOdd<2>
EvenOdd<3>
EvenOdd<4>
EvenOdd<5>
EvenOdd<6>
EvenOdd<7>
EvenOdd<8>
EvenOdd<9>
EvenOdd<10>
std::cout << "Hey!" << std::endl;
Print<9>
Print<8>
Print<7>
Print<6>
Print<5>
Print<4>
Print<3>
Print<2>
Print<1>
Print<0>
偶数
偶数
偶数
偶数
偶数
偶数
偶数
偶数
偶数
偶数
偶数
标准::cout
EvenOdd<0>
EvenOdd<1>
EvenOdd<2>
EvenOdd<3>
EvenOdd<4>
EvenOdd<5>
EvenOdd<6>
EvenOdd<7>
EvenOdd<8>
EvenOdd<9>
EvenOdd<10>
std::cout << "Hey!" << std::endl;
Print<9>
Print<8>
Print<7>
Print<6>
Print<5>
Print<4>
Print<3>
Print<2>
Print<1>
Print<0>