我有一段代码,它应该声明基础结构,然后声明继承它的模板结构。然后结构部分被证明。
#include <utility>
#include <iostream>
template<class A, class B>
struct Parent {
std::pair<A, B> m_pair;
void print() {
std::cout << m_pair.first << ", " << m_pair.second << "\n";
}
};
template <class A, class B>
struct Some : public Parent<A, B> {
Some(A a, B b) : Parent<A, B>({ {a, b} }) {}
void add() {
m_pair.first += m_pair.second;
}
};
template <class B>
struct Some<B, float> : public Parent<B, float> {
Some(B a, float b) : Parent<B, float>({ {a, b} }) {}
void add() {
m_pair.first -= m_pair.second;
}
};
int main() {
Some<int, float> s(4, 42);
s.add();
s.print();
return 0;
}
当我在Visual Studio 2015中编译它时,一切都编译得很好,并按预期工作。但是,当我使用GCC 5.2.1或clang 3.6编译时,我得到以下错误:
untitled.cpp: In member function ‘void Some<A, B>::add()’:
untitled.cpp:17:9: error: ‘m_pair’ was not declared in this scope
m_pair.first += m_pair.second;
^
untitled.cpp: In member function ‘void Some<B, float>::add()’:
untitled.cpp:24:9: error: ‘m_pair’ was not declared in this scope
m_pair.first += m_pair.second;
怎么了?但是,当我将m_pair
称为Parent<A, B>::m_pair
时,它可以在GCC和clang中使用。
定义标准模板clasess(使用特定方法)的正确方法是什么,它们共享常用方法?
答案 0 :(得分:5)
由于基类依赖于模板参数,因此在非限定名称查找期间不会检查基本成员。
幸运的是,修复很简单:只需使用this->
:
this->m_pair.first += this->m_pair.second;
this->m_pair.first -= this->m_pair.second;
此将查看基类,因此将找到该成员。
非限定查找在MSVC中有效,因为该编译器在其模板实现的许多方面都不符合。