根据条款43,这两个方法是一个作用啊
附上别人的条款43,44的链接
https://blog.csdn.net/gx864102252/article/details/76944704
的确,既然子类using了基类的invert,那么在子类中调用基类的invert函数,"this->"不是必要的,去掉"this->"代码也能通过编译。但是,如果去掉"using SquareMatrixBase<T>::invert",那么"this->invert(n)"不能通过编译。因为子类的invert隐藏了基类的同名函数。以下两种情形,在子类中使用using将基类的函数引入:
1)当子类的函数隐藏了基类的同名函数时,使用using引入基类的同名函数使其在子类中可见;
2)当基类是类模板,在子类中调用基类的某个函数时,使用using引入基类的函数以指示编译器在基类中查找此函数的声明。
参考下面的代码:
// 情形1
class Base
{
public:
void f() { cout << "Base::f()" << endl; }
void g() { cout << "Base::g()" << endl; }
};
class Sub : public Base
{
public:
void f(int arg) // 隐藏了基类的f
{
// f(); // error : “Sub::f”: 函数不接受 0 个参数.
cout << "Sub::f(int), arg : " << arg << endl;
}
using Base::g; // 引入基类的函数g
void g(int arg) // 重载g
{
g(); // ok, 调用Base::g()
cout << "Sub::g(int), arg : " << arg << endl;
}
};
void example1()
{
Sub sub;
//sub.f(); // error : “Sub::f”: 函数不接受 0 个参数.
sub.f(1); // ok
sub.g(); // ok
sub.g(2); // ok
}
// 情形2
template <typename T>
class BaseT
{
public:
void f1(T arg) { cout << "BaseT::f1(T), arg : " << arg << endl; }
void g1(T arg) { cout << "BaseT::g1(T), arg : " << arg << endl; }
void h1(T arg) { cout << "BaseT::h1(T), arg : " << arg << endl; }
};
template <typename T>
void h1(T arg) { cout << "::h1(T), arg : " << arg << endl; }
template <typename T>
class SubT : public BaseT<T>
{
public:
void f2(T arg)
{
// f1(arg); // error: “f1”: 找不到标识符.
printf("SubT::f2(T), arg : %d\r\n", arg);
}
using BaseT<T>::g1; // 在基类中查找g1
void g2(T arg)
{
g1(arg); // ok, 调用Base<T>::g1(T)
printf("SubT::g2(T), arg : %d\r\n", arg);
}
void h2(T arg)
{
h1(arg); // ok, 调用::h1<T>(T).
printf("SubT::g2(T), arg : %d\r\n", arg);
}
};
void example2()
{
SubT<int> sub;
sub.f2(1);
sub.g2(2);
sub.h2(3);
}
注意SubT的成员函数f2的定义,h1(arg)
调用的是全局作用域的函数h1,而不是基类的成员函数h1。如果一个类的基类依赖于模板参数,那么对于无限定名字,编译器不会查找基类的作用域,在类的定义点和实例化点都不会。有关名字查找的详细内容,请参考:https://zh.cppreference.com/w/cpp/language/lookup