在TypeScript中声明关键字的目的

时间:2017-04-11 02:49:20

标签: typescript typescript2.0

declare关键字的目的是什么?

type Callback = (err: Error | String, data: Array<CalledBackData>) => void;

VS

declare type Callback = (err: Error | String, data:Array<CalledBackData>) => void;

无法找到解释TS中declare关键字用途的文档。

6 个答案:

答案 0 :(得分:20)

tl; dr

'declare'用来告诉编译器'这个东西(通常是一个变量)已经存在,因此可以被其他代码引用,也不需要将该语句编译成任何JavaScript”

常见用例:

您将对网页的引用添加到编译器一无所知的JavaScript文件中。也许这是一个来自其他域名(例如“ foo.com”)的脚本。经过评估,脚本将创建并使用一些有用的api方法进行对象化,并将其分配给全局范围内的标识符'fooSdk'。

您希望您的TypeScript代码能够调用'fooSdk.doSomething()',但是由于您的编译器不知道该变量存在,因此会出现编译错误。

然后,您使用声明关键字作为一种告诉编译器“信任我,该变量存在并且具有这种类型”的方式。编译器将使用此语句来静态检查其他代码,但不会将其反编译为输出中的任何JavaScript。

declare const fooSdk = { doSomething: () => boolean };

同样,您可以在类属性中添加define关键字,以告诉编译器不要发出任何会创建该属性的代码,前提是您拥有自己的代码来创建该属性,而编译器对此一无所知不明白。

您的特定示例有所不同,因为您声明的是类型,而不是变量,所以类型已经不能编译为任何JavaScript。我不知道是否有任何理由来声明类型。

答案 1 :(得分:5)

我从谷歌得到的第一个结果表明:

  

declare关键字用于环境声明,您可以在其中定义可能不是源自TypeScript文件的变量。

http://blogs.microsoft.co.il/gilf/2013/07/22/quick-tip-typescript-declare-keyword/

答案 2 :(得分:4)

这是一个真实的例子。

我有一个使用Webpack Hot Middleware的TypeScript React应用程序。 Webpack中间件不是用TypeScript编写的,而是老式的JavaScript。 因此,它没有类型脚本编译器可以检查的类型声明。

因此,当我运行代码时, Webpack Hot Middleware中的对象module确实存在,并且我也可以console.log它,尽管它是老式的JavaScript,并且隐藏在我喜欢的新TypeScript React应用程序中。

module对象还具有键,例如 'module.hot',并且键可以具有值 但是至少在VSCode中的TypeScript设计时编译器在其下写着一个红色的波浪形 property 'hot' does not exist

但是我说它确实存在。

要使TypeScript编译器同意, 声明它,就像

declare let module: any

现有的module对象现在具有一种any类型,这使TypeScript编译器现在感到高兴,红色蠕动消失了,现在我可以继续编译并编写将改变的突破性代码世界。

此外,如果删除关键字declare,而只写let module: any,则不会编译为'module' already exists。所以我想这就是环境的意思。

答案 3 :(得分:3)

来自Typescript文档:

Typescript - Working with Other JavaScript Libraries

要描述不是用TypeScript编写的库的形状,我们需要声明该库公开的API。由于大多数JavaScript库仅公开一些顶级对象,因此名称空间是表示它们的好方法。

我们将未定义实现的声明称为“环境”。通常,这些声明是在.d.ts文件中定义的。如果您熟悉C / C ++,则可以将它们视为.h文件。让我们看几个例子。

环境命名空间

流行的库D3在名为d3的全局对象中定义其功能。由于此库是通过标签(而不是模块加载器)加载的,因此其声明使用名称空间来定义其形状。为了让TypeScript编译器看到这种形状,我们使用环境名称空间声明。例如,我们可以开始编写如下代码:

D3.d.ts(简化摘录)

declare namespace D3 {
    export interface Selectors {
        select: {
            (selector: string): Selection;
            (element: EventTarget): Selection;
        };
    }
    // (...)
}

答案 4 :(得分:0)

delcare关键字在导入某些没有声明类型文件的库时使用,例如* .d.ts

在此之后,vs eslint不检查语法和上下文,如果您默认使用tsc编译器,它将让您通过声明删除语法错误的充分理由

答案 5 :(得分:0)

您可以在编写任何实现代码之前使用声明将类型告诉编译器,这样TypeScript就会感到满意。

declare function foo(name: string): string