0

I found interesting question and decided to examine top answer in detail.
I asked myself why there needs structure and try to rewrote the code without it:

#include <iostream>
template <int N> void out(std::ostream& os) {
    out<N-1>(os);
    os << N << std::endl;
}

template <> void out<1>(std::ostream& os){
    os << 1 << std::endl;
}

int main(){
    out<100>(std::cout);
}

And then I tried to refactor the code. I got something like this:

#include <iostream>
template <int N> void out() {
    if (N != 1) {
        out<N-1>();
        std::cout << N << std::endl;
    }
    else {
        std::cout << 1 << std::endl;
    }
}

int main(){
    out<100>();
}

I don't understand why this code didn't work.
Any ideas?

Community
  • 1
  • 1
evlogii
  • 811
  • 1
  • 7
  • 17
  • 4
    the branch is a run time construct, the compiler will happily instantiate `out` which will carry on... The whole purpose of the specialization is to terminate the instantiations.. – Nim Apr 18 '13 at 14:08

2 Answers2

5

The problem is that the if condition is evaluated at run-time. When you get to the instantiation where N = 1, it doesn't know that the first block of the if statement won't execute. It proceeds to instantiate out<0> and so on. If we had a static if, this would be possible, but it probably won't happen very soon.

Joseph Mansfield
  • 108,238
  • 20
  • 242
  • 324
3

Templates are expanded during compilation while if statements are only checked during run-time which is a different later stage. In your case the compiler will try to expand indefinetely as there is no specific implementation of the function for a fixed value of N(that used to be 1).

Ivaylo Strandjev
  • 69,226
  • 18
  • 123
  • 176