在Typescript 2.x中创建命名空间

时间:2017-05-04 14:45:28

标签: typescript namespaces typescript2.0

我已经阅读了(再次)使用Typescript的文档来清除模块和命名空间的内容,但我仍然有一些暗点。

  1. declare namespace Foo{}
  2. namespace Foo{}
  3. export namespace Foo{}
  4. 在这3种创建命名空间的方法中,每种方法的用途是什么?

    假设我想创建一个 Validation 命名空间,我有3个文件可以为该命名空间做出贡献。这样做的正确方法是什么,以及如何从另一个文件/模块导入(使用)Validation命名空间中的代码?

1 个答案:

答案 0 :(得分:2)

  

这样做的正确方法是什么以及我将如何进行   从另一个文件/模块导入(使用)Validation命名空间中的代码?

当您在一个问题中说“导入(使用)”和“文件/模块”时,您会询问两种截然不同的情况,每种情况的答案都不同。

使用import和模块无法做到这一点。每个模块都是一个独立的,独立的范围,如果在每个模块中定义namespace Validation,您将创建3个不同的命名空间,因为不合并来自不同范围的声明。好吧,你可以使用declare global打破模块范围,但它违背了模块的既定目的 -  消除全局变量。

您可以使用非模块的文件(即没有任何顶级importexport的文件)来执行此操作。但是,你只能使用非模块化的javascript(或打字稿)。您的namespace Validation将在全局范围内,您不能使用import和模块,并且您必须编译并连接所有文件,生成适合使用<script>加载的单个脚本标签

另见How do I use namespaces with TypeScript external modules?

至于具体的语法变体

declare namespace Foo {}

这声明存在名称空间Foo,在某个外部文件中定义(未包含在当前编译中),允许使用Foo,假定它包含在{}中声明的内容(和{{ 1}}可能只包含声明,而不包含定义)

{}

这会创建名称空间namespace Foo {}

Foo

这也会创建名称空间Foo,但export namespace Foo {} 可能有不同的含义,具体取决于它在源文件中的位置(它还取决于文件是否是模块,但我不想详细了解export如何在没有模块的情况下有用)。

如果export位于顶层,则会将文件转换为模块,并使export可用于导入和使用(但不扩展)其他模块。如果Foo不在顶层,那么它又取决于:如果它在某个导出的命名空间中,它定义嵌套的命名空间,可由导入该外​​部命名空间的模块访问。如果它在非导出的命名空间中,export没有效果,我相信。