classBase{ protected: int bn1; int bn2; }; classDerived: private Base{ public: using Base::bn1; }; classDerivedAgain: public Derived{ }; intmain(){ Derived d; DerivedAgain da; d.bn1 = 1; d.bn2 = 2; //error, 'bn2' is a private member of 'Base' da.bn1 = 3; //ok std::cout<<d.bn1<<std::endl; return0; }
盡管 Derived 對 base 是私有繼承,但通過 using 聲明,我們還是可以在 Derived 中訪問其成員,
且後續的繼承同樣不受 private 限定的影響。
2. using 指示 (引入命名空間)
using 指示 (using directive) 是使一個命名空間中的 所有 名字都在該作用域中可見的機製。
這是最常用的方式了。需要註意的是命名沖突問題。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
#include<iostream> namespace n1{ int n1_member = 10; int m = 11; } int m = 12; intmain(){ usingnamespace n1; std::cout<<n1_member<<std::endl; //std::cout<<m<<std::endl; //error 命名沖突 std::cout<<::m<<std::endl; int m = 13; //ok, 局部變量屏蔽命名空間變量 std::cout<<m<<std::endl; return0; }
Notice: 盡管 using指示很方便,但在實際工作中應該盡量避免:
它一下子將另一個 namespace 中的成員全部引入了,一不小心就會出現命名空間汙染問題。
3. 類型重定義,取代 typedef
1
using alias = typename
這是 C++11 中的新用法,比 typedef 更能表達別名的定義。
1 2 3 4 5 6 7 8
using fun = void (*)(int, int); //typedef void (*fun)(int, int); //與上一句等價 using int16 = short; //typedef short int16; //與上一句等價 intmain(){ std::cout<<sizeof(int16)<<std::endl; }