错误 C2760:语法错误:意外的标记“标识符”,预期为“;” 在地图迭代器

S.F*_*rrd 2 c++

我创建了一个继承std::map并尝试使用方法在特定索引处获取值的类。

#define MYAPI_EXPORTS
#ifdef MYAPI_EXPORTS  
#define MY_API __declspec(dllexport)
#else  
#define MY_API __declspec(dllimport)   
#endif

    template<class _Value>
    class MY_API MyDictionary : public std::map<std::string, _Value>
    {
        _Value GetItem(int index)
        {
            std::map<std::string, _Value>::iterator itr = this->begin(); //compile error at this line

            int c = 0;
            while (c < index)
            {
                itr++;
                c++;
            }
            return itr->second;
        }
    };
Run Code Online (Sandbox Code Playgroud)

'std::map::iterator itr' 这一行在编译时显示错误。

错误是

error C2760: syntax error: unexpected token 'identifier', expected ';'
error C7510: 'iterator': use of dependent type name must be prefixed with 'typename'
Run Code Online (Sandbox Code Playgroud)

似乎在编译时没有定义迭代器类型。有没有办法解决这个问题?

zco*_*vid 8

您可以通过以下方式修复它:

typename std::map<std::string, _Value>::iterator itr = this->begin();
Run Code Online (Sandbox Code Playgroud)

或者

auto itr = this->begin();
Run Code Online (Sandbox Code Playgroud)


Lig*_*ica 6

错误消息准确地告诉您可以做什么:

   typename std::map<std::string, _Value>::iterator itr = this->begin();
// ^^^^^^^^^
Run Code Online (Sandbox Code Playgroud)

......但不是你必须这样做的原因。

简而言之,这是C++中与模板和所谓的“从属名称”相关的怪癖。因为是一个模板参数,并且因为存在模板特化,所以 C++直到稍后在解析过程中_Value才能确定是否std::map<std::string, _Value>具有成员类型。iterator因此,您的声明格式不正确,因为编译器即使眯起眼睛也无法完全将其视为声明。typename说“这将是一种类型,我保证”,然后一切都很好(只要它确实是一种类型!)。

您可能认为这应该是 C++ 的问题,而不是您的问题,您可能是对的,但事实就是这样。您可以搜索更多关于此的信息,或者只是想当然地认为,当编译器告诉您编写时typename,您就编写typename

或者,通过使用以下方法,使代码变得更好并同时解决问题auto

auto itr = this->begin();
Run Code Online (Sandbox Code Playgroud)

顺便说一句,你的代码表明你使用了错误的容器,GetItem应该是,你不const应该使用(尽管如果你遵循建议,这已经为你完成了),并且已经存在......cbegin()begin()conststd::advance