简体   繁体   中英

Why am I getting zero?

In this code (ready to compile):

      #include "stdafx.h"
        #include <iostream>
        #include <sstream>

        using std::cout;

        template<class T, int first, int second>
        T make()
        {
            T result = T();
            std::stringstream interpreter;
            interpreter << first << '.' << second;
            interpreter >> result;
            return result;
        }

 template<int first, int second, class T = double>
    struct Make
    {
        typedef T value_type;
        static value_type value;

    };

    template<int first, int second, class T>
    T Make<first,second,T>::value = make<T,first,second>();



    template<int first, int second>
    struct Real
    {
        typedef double type;
        static type value;
    };

        template<int first, int second>
    typename Real<first,second>::type typename Real<first,second>::value = typename Make<first,second>::value;  


       int _tmain(int argc, _TCHAR* argv[])
    {
        //cout << Make<1,2>::value << '\n';//UNCOMMENT THIS AND SEE WHAT I MEAN
        cout << Real<1,2>::value;
        return 0;
    }

Please see the comment 4 lines above.

That isn't ready to compile (you don't use typename where you expect a variable name). After fixing those things, I get 1.2 for both:

http://codepad.org/z3UCiOfK

http://codepad.org/66xnnLbd

Edit: It didn't work in VS 2005. This must be a problem in VC++ (at least in 2005). It's probably related to how they do certain template processing later than the standard requires. That's just a guess, though.

If you call Real<1,2>::value before you call Make<1,2>::value, it gets initialized first, so it gets Make<1,2>::value's initial non-initialized value, which is 0.

If you call Make<1,2>::value first, it gets initialized properly with the make() function, it gets the value 1.2. Then, since Real<1,2>::value gets initialized afterwards, it gets that value.

This works for me with two tweaks, remove the redundant typename decelerations:

template<int first, int second>
typename Real<first,second>::type typename Real<first,second>::value = typename Make<first,second>::value;  

becomes:

template<int first, int second>
typename Real<first,second>::type Real<first,second>::value = Make<first,second>::value;

(at least in gcc 4.4.4)

The result is 1.2, 1.2 - which is as expected(?)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM