Appearance
基础篇-模块和命名空间
模块
ES6
导出
js
// ./src/es6/a.ts
// 单独导出
export const a = 1
// 批量导出
const b = 2
const c = 3
export { b, c }
// 导出接口
export interface P {
x: number
y: number
}
// 导出函数
export function fn () {}
// 导出时起别名
export { fn as Fn }
// 默认导出
export default () => { console.log('I am a function') }
// 引入外部模块,重新导出
// ./src/es6/a.ts
// export const str = 'b'
export { str as Str } from './b'
ES6 导出使用 export 关键字,如上所示可以单独导出变量、对象、接口、函数等等
导入
js
// ./src/es6/c.ts
import { a, b, c } from './a'; // 批量导入
import { P } from './a'; // 接口导入
import { fn as F } from './a'; // 导入时设置别名
import * as All from './a'; // 导入所有成员
import defaultFuntion from './a'; // 导入默认
console.log(a, b, c); // 1 2 3
let p: P = {
x: 1,
y: 2,
};
F();
/**
* {
* __esModule: true,
* a: 1,
* b: 2,
* c: 3,
* fn: [Function: fn],
* Fn: [Function: fn],
* default: [Function],
* Str: 'b'
* }
*/
console.log(All);
defaultFuntion(); // I am a function
ts 中的导入导出与 js 大致相同。
CommonJS
导出
ts
// ./src/node/a.node.ts
let a = {
x: 1,
y: 2,
};
module.exports = a;
module.exports 整体导出
js
// ./src/node/b.node.ts
exports.c = 3;
exports.d = 4;
exports 导出多个变量,若这里再设置了 module.exports 会覆盖调 exports 所有导出的定义。
导入
CommonJS 导入:
ts
// ./src/node/c.node.ts
let c1 = require('./a.node');
let c2 = require('./b.node');
console.log(c1); // { x: 1, y: 2 }
console.log(c2); // { c: 3, d: 4 }
这里需要注意,引入文件时未添加文件名后缀.ts,当用 node 命令执行时,默认会找 js 文件,这里有以下解决方案
- 1、编译成
js后执行 - 2、添加
ts后缀 - 3、安装
ts-node,npm install ts-node -g
当 CommondJS 引入 es6 输出时,调用默认导出时需要调用 default 属性。
ts
let es6 = require('../es6/a');
es6.default(); // I am a function
若使用 export = 形式导出时,相当于 CommonJS 的顶级导出 module.exports =
ts
// ./src/es6/d.ts
export = () => {
console.log('I am a function');
};
let d = require('../es6/d');
d(); // I am a function
命名空间
在 JavaScript 中,命名空间能有效的避免全局污染。在 es6 引入了模块系统之后,命名空间就很少被使用了。但 TS 中依然实现了这个特性,尽管在模块系统中,我们不必考虑全局污染情况,但如果使用了全局的类库,命名空间仍然是一个比较好的解决方案。
例子
首先创建两个 ts 文件,分别为 a.ts 和 b.ts 代码如下:
本篇大部分为代码段,可以点击查看源码运行阅读。
ts
// ./src/a.ts
namespace Shape {
const pi = Math.PI;
export function cricle(r: number) {
return pi * r ** 2;
}
}
如果让成员在全局可见,需要使用 export 关键字输出。
ts
// ./src/b.ts
namespace Shape {
export function square(x: number) {
return x * x;
}
}
console.log(Shape.cricle(1));
console.log(Shape.square(1));
同样在 b.ts 文件中也声明了命名空间,在底部调用了 Shape.cricle 和 Shape.square 两个方法。
这时我们进行编译的话,因为 cricle 属性存在于 a.ts 文件内,会报出 error TS2339: Property 'cricle' does not exist on type 'typeof Shape'. 错误,这里我们可以使用三斜线指令