正确的模板类'内部类的映射迭代器的语法?

Sto*_*row 7 c++ templates dictionary stl inner-classes

我想请求帮助正确的语法来声明一个std :: map,其mapped_type是模板类的内部类.

请在下面的代码中找到#if /#else块."#if 1"块具有包含内部类Inner的模板类Outer.外部定义了函数Func,它采用了一个std映射,其mapping_type是Inner类型.

#include <map>

#if 1
template<typename C, typename T>
class Outer
{
    public:
        Outer(const C& c, const T& t){}
        virtual ~Outer(){}

        class Inner
        {
            public:
                Inner(){}
                Inner(T t){}
                virtual ~Inner(){}

            protected:
                T mT;
        };

        void Func(std::map<C, Inner>& rMap);

    protected:
        std::map<C, Inner> mMap;
};

template<typename C, typename T>
void Outer<C, T>::Func(std::map<C, Outer::Inner>& rMap)
{
    std::map<C, Inner>::iterator iter;

    for (iter = rMap.begin(); iter != rMap.end(); ++iter)
    {
        mMap[iter->first] = iter->second;
    }
}

#else

class Outer
{
    public:
        Outer(const int& i, const double& d){}
        virtual ~Outer(){}

        class Inner
        {
            public:
                Inner() : mD(0){}
                Inner(const double d) : mD(d){}
                virtual ~Inner(){}

            protected:
                double mD;
        };

        void Func(std::map<int, Inner>& rMap);

    protected:
        std::map<int, Inner> mMap;
};

void Outer::Func(std::map<int, Inner>& rMap)
{
    std::map<int, Inner>::iterator iter;

    for (iter = rMap.begin(); iter != rMap.end(); ++iter)
    {
        mMap[iter->first] = iter->second;
    }
}

#endif

int main()
{
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

在stout :: map迭代器的声明中,编译在Outer :: Func(...)中失败,即此行:

std::map<C, Inner>::iterator iter;
Run Code Online (Sandbox Code Playgroud)

我已经尝试但无法弄清楚代码行有什么问题.

对于比较/对比,"#else"块包含类似性质的非模板代码.这段代码编译.

编译错误和g ++版本是:

>g++ main.cpp
main.cpp: In member function ‘void Outer<C, T>::Func(std::map<C, Outer<C, T>::Inner, std::less<_Key>, std::allocator<std::pair<const C, Outer<C, T>::Inner> > >&)’:
main.cpp:31: error: expected ‘;’ before ‘iter’
main.cpp:33: error: ‘iter’ was not declared in this scope

>g++ --version
g++ (GCC) 4.4.7 20120313 (Red Hat 4.4.7-11)
Copyright (C) 2010 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
Run Code Online (Sandbox Code Playgroud)

感谢您的任何帮助.

nsh*_*hct 9

由于Inner是模板的成员Owner<C, T>,因此它将成为依赖名称.这导致标识符iterator(在这种情况下是其成员)std::map<C, Inner>成为依赖名称.

这会强制您typename根据规则使用关键字:

typename std::map<C, Inner>::iterator iter;
~~~^~~~~
Run Code Online (Sandbox Code Playgroud)

这是因为编译器无法确定类内部的某些结构是什么意思,因为它不知道用于的确切类型C,T但是:

在模板的定义(类模板和函数模板)中,一些构造的含义可能因实例而异.特别地,类型和表达式可以取决于类型模板参数的类型和非类型模板参数的值.

typename关键字用于告诉编译器您正在访问的符号确实是类型别名/类型.