TypeScript中的declare:为什么需要它以及如何使用它

面向初学者的在线Python训练器

轻松学习Python,无需理论负担。在浏览器中直接解决带自动检查的实践任务,无需安装任何东西。

开始课程

为什么TypeScript需要declare关键字?

\n

想象一下,你在建造一栋房子,但有些房间已经存在了——它们是别人建造的(比如JavaScript库)。你无法进去重新砌墙,但你需要知道它们的布局,才能正确摆放家具。这正是TypeScript中declare关键字所扮演的角色。

\n\n

如果你曾经使用过流行的库(jQuery、Lodash、D3.js),那么你一定遇到过.d.ts文件——这些就是用declare创建的“布局图”。在本文中,我们将深入探讨什么是declare,为什么需要它,以及如何在实际中使用它。准备好——会有很多代码,很少废话。

\n\n

TypeScript中的declare是什么?

\n

declare是一个关键字,它告诉TypeScript编译器:“嘿,这个东西(变量、函数、类或模块)是存在的,但它是在其他地方定义的。你只要相信我,让我在代码中使用它就行了。”

\n\n

重要的是要理解:declare不会生成任何JavaScript代码。它纯粹是给编译器用的信息性结构。如果你写declare const x: number = 5,编译后x就会消失——它不会出现在最终文件中。

\n\n

什么时候需要它?

\n
    \n
  • 处理全局变量——例如window、document或通过CDN添加的变量。
  • \n
  • 为JavaScript库添加类型——当库是用纯JS编写的,但你希望将其与TypeScript一起使用时。
  • \n
  • 为配置文件创建类型——CSS模块、图片、JSON文件。
  • \n
\n\n

declare语法:基本示例

\n\n

1. 变量声明

\n

假设你有一个全局变量VERSION,它是在HTML文件中通过<script>定义的。TypeScript对此一无所知,因此你编写:

\n
declare const VERSION: string;\n\nconsole.log(VERSION); // 没问题,TypeScript知道这是一个字符串\n
\n

编译后,declare const VERSION: string会消失,而console.log(VERSION)会保留。

\n\n

2. 函数声明

\n

假设你有一个来自分析工具的全局函数trackEvent:

\n
declare function trackEvent(eventName: string, properties?: Record<string, any>): void;\n\n// 使用\ntrackEvent("button_click", { buttonId: "submit" });\n
\n

编译器不会检查实现——它只知道函数签名。

\n\n

3. 类声明

\n

一个库提供了全局命名空间中的Moment类:

\n
declare class Moment {\n    constructor(date: string);\n    format(pattern: string): string;\n}\n\n// 使用\nconst now = new Moment("2024-01-01");\nconsole.log(now.format("YYYY-MM-DD"));\n
\n\n

4. 模块声明

\n

这是最常见的场景。例如,你有CSS模块或JSON文件:

\n
// styles.d.ts\ndeclare module "*.css" {\n    const styles: Record<string, string>;\n    export default styles;\n}\n\n// images.d.ts\ndeclare module "*.png" {\n    const src: string;\n    export default src;\n}\n
\n

现在你可以导入CSS和图片而不会出现TypeScript错误。

\n\n

declare和.d.ts文件

\n

扩展名为.d.ts的文件(类型声明文件)是declare关键字的“栖息地”。它们只包含声明,不会编译成JavaScript。通常它们位于types/文件夹中,或者随库一起提供(例如@types/lodash)。

\n\n

示例:为jQuery创建类型

\n

博客

书籍推荐