WHCSRL 技术网

C++ Primer 5th笔记(chap 18 大型程序工具)使用命名空间成员

1. 3种方法

  • using 声明
  • 命名空间的别名( namespace alias)
  • using 指示( using directive)

1.1 命名空间的别名

namespace cplusplus_primer { /* ... / ;}
namespace primer = cplusplus_primer;
  • 1
  • 2

命名空间的別名也可以指向一个嵌套的命名空间:

namespace Qlib = primer::QueryLib;
Qlib::Query q;
  • 1
  • 2

一个命名空间可以有好几个同义词或别名, 所有别名都与命名空间原来的名字等价

1.2 using 声明( using declaration)

一条 using 声明( using declaration) 语句一次只引入命名空间的一个成员

using 声明的名字的作用域与 using 声明语句本身的作用域一致

eg.

using nsl::Student;
//在用上面的using声明后,在其后程序中出现的Student就是隐含地指nsl::Student
  • 1
  • 2

1.2.1 作用域

有效范围从using声明的地方开始,一直到using声明所在的作用域结束为止

未加限定的名字只能在using声明所在的作用域以及内层作用域中使用

一条using声明可以出现在全局作用域、局部作用域、命名空间作用域以及类的作用域中;在类的作用域中,这样的声明语句只能指向基类成员(因为派生类只能为那些它可以访问的名字提供using声明)

当命名空间被注入到它的外层作用域之后,很有可能该命名空间中定义的名字会与其外层作用域中的成员冲突。这种冲突是允许存在的,但是要想使用冲突的名字,我们就必须明确指出名字的版本

namespace blip {
     int bi = 16, bj = 15, bk = 23;
     // other declarations
     
    int bj = 0; // ok: bj inside blip is hidden inside a namespace
    void manip()
    {

         // using directive - names in blip "added" to global scope
         using namespace blip;
                         // clash between ::bj and blip::bj
                         // detected only if bj is used
         ++bi;           // sets blip::bi to 17
         ++bj;           // error: ambiguous
                         // global bj or blip::bj?
         ++::bj;         // ok: sets global bj to 1
         ++blip::bj;     // ok: sets blip::bj to 16
         int bk = 97;    // local bk hides blip::bk
         ++bk;           // sets local bk to 98
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21

1.2.2. 头文件与 using 声明或指示

头文件如果在其顶层作用域中含有 using 指示或 using 声明, 则会将名字注入到所有包含了该头文件的文件中。

通常情况下, 头文件应该只负责定义接口部分的名字, 而不定义实现部分的名字。 因此, 头文件最多只能在它的函数或命名空间内使用 using 指示或 using 声明

推荐阅读