TypeScript(简称 TS)是一种由微软开发的开源编程语言,它是 JavaScript 的超集,扩展了 JavaScript 的语法。TypeScript 通过添加静态类型、接口、类等特性,使得 JavaScript 代码更加规范和易于维护。本文将详细介绍 TypeScript 的基础知识、安装与配置、常见语法以及如何使用 TypeScript 进行开发。
一、TypeScript 简介
1.1 什么是 TypeScript?
TypeScript 是一种基于 JavaScript 的编程语言,它在 JavaScript 的基础上添加了静态类型检查、接口、类等特性。TypeScript 代码最终会被编译成 JavaScript 代码,因此可以在任何支持 JavaScript 的环境中运行。
1.2 为什么使用 TypeScript?
-
规范书写:TypeScript 提供了类型检查,帮助开发者在编码阶段发现潜在的错误,提升代码质量。
-
预警提示:TypeScript 在编译时会提示类型错误,减少运行时错误。
-
提升编码效果:TypeScript 提供了代码补全、参数提示等功能,提升开发效率。
-
易于维护:TypeScript 的静态类型和接口等特性使得代码更易于理解和维护。
1.3 TypeScript 学习文档
二、TypeScript 安装与配置
2.1 安装 TypeScript
TypeScript 可以通过 npm 全局安装:
npm install -g typescript
安装完成后,可以通过 tsc
命令来编译 TypeScript 文件。
2.2 初始化 TypeScript 项目
-
创建一个项目目录,并在该目录下打开终端。
-
初始化
tsconfig.json
文件:tsc --init
-
配置
tsconfig.json
文件:{ "compilerOptions": { "module": "system", "noImplicitAny": true, "removeComments": true, "preserveConstEnums": true, "outFile": "./dist/main.js", "outDir": "dist", "sourceMap": true }, "include": ["src/*.*"], "exclude": ["node_modules", "**/*.spec.ts"] }
2.3 项目结构
一个典型的 TypeScript 项目结构如下:
|---- web
|---- dist
| |---- main.js
|---- src
| |---- index.ts
|---- tsconfig.json
2.4 编译 TypeScript 文件
-
编译单个文件:
tsc index.ts
-
监视
src
目录下的所有 TypeScript 文件,并输出到dist
目录:tsc --watch
三、TypeScript 基础语法
3.1 变量声明
TypeScript 支持多种数据类型,如 number
、string
、boolean
、any
等。
let src: string = '/static/imgs/1.jpg';
let age: number = 20;
let isMale: boolean = true;
let anything: any = '可以是任意类型';
3.2 函数
TypeScript 允许对函数的参数和返回值进行类型约束。
// 示例1:无返回值的函数
const sayHello = (userName: string): void => {
console.log(`${userName}, 你好。`);
}
sayHello("张三");
// 示例2:有返回值的函数
const getRandomNum = (min: number, max: number): number => {
return Math.floor(Math.random() * (max - min) + min);
}
let v1: number = getRandomNum(50, 100);
console.log(v1);
3.3 接口
接口用于规范对象的结构。
interface User {
nickName: string;
account: string;
password: string | number;
age?: number; // 可选参数
}
let zhangsan: User = {
nickName: "张三",
account: "666666@qq.com",
password: 123456,
age: 20
}
const showInfo = (person: User): void => {
console.log(person);
}
showInfo({
nickName: "李四",
account: "1111@qq.com",
password: 123123
});
3.4 枚举
枚举用于定义一组常量。
enum Direction {
Up = 38,
Down = 40,
Left = 37,
Right = 39
}
console.log(Direction.Down); // 40
enum Api {
search = '/api/search',
list = '/api/list',
login = '/api/login',
register = '/api/register'
}
console.log(Api.search); // /api/search
3.5 泛型
泛型允许在定义函数或类时不指定具体类型,而是在使用时再指定。
function foo<T>(a: any): T {
return a.replace(/\s/g, '');
}
console.log(foo<string>('he llo wor ld')); // helloworld
const sayHello = <A>(user: A): A => {
console.log(`${user}, 你好`);
return user;
}
let v1 = sayHello<string>('小明'); // 小明
let v2 = sayHello<number>(2024); // 2024
3.6 类型断言
类型断言用于告诉编译器某个值的类型。
const canvas = document.querySelector("#canvas") as HTMLCanvasElement;
console.dir(canvas);
3.7 type
语法
type
语法用于定义类型别名,常用于描述对象的结构。
type ZUOBIAO = {
x: number,
y: number,
z?: number | string
} & {
color: string
}
let point1: ZUOBIAO = {
x: 100,
y: 200,
z: "300px",
color: "blue"
}
3.8 类
TypeScript 支持面向对象编程,可以使用类来定义对象的结构和行为。
interface Opt {
name: string,
age: number,
sayHello: Function,
constructor: Function
}
class Person implements Opt {
name: string;
age: number;
constructor(name: string, age: number) {
this.name = name;
this.age = age;
}
sayHello() {
console.log(`${this.name}今年${this.age}岁`);
}
}
const p1 = new Person('张三', 18);
p1.sayHello(); // 张三今年18岁
3.9 修饰符
TypeScript 提供了 public
、private
、protected
等修饰符来控制类成员的访问权限。
class Draw {
public x = 50;
public y = 100;
private privateX = 50;
protected protectedY = 100;
}
class DrawCircle extends Draw {
r: number = 200;
show() {
console.log(`绘制一个半径${this.r},在x:${this.x}, y:${this.protectedY}位置的圆。`);
}
}
const dc = new DrawCircle();
dc.show(); // 绘制一个半径200,在x:50, y:100位置的圆。
3.10 抽象类
抽象类不能被实例化,只能被继承。
abstract class User {
account: string;
password: string;
constructor(acc: string, pwd: string) {
this.account = acc;
this.password = pwd;
}
}
class Student extends User {}
class Teacher extends User {}
const s1 = new Student("学生账号", "123123");
console.log(s1.account); // 学生账号
console.log(s1.password); // 123123
四、TypeScript 进阶知识点
4.1 联合类型与交叉类型
4.1.1 联合类型
联合类型允许一个变量可以是多种类型中的一种。
let value: string | number;
value = "Hello"; // 合法
value = 42; // 合法
// value = true; // 报错,boolean 不是 string 或 number
4.1.2 交叉类型
交叉类型将多个类型合并为一个类型,通常用于组合多个接口。
interface A {
name: string;
}
interface B {
age: number;
}
type C = A & B;
let person: C = {
name: "张三",
age: 20
};
4.2 类型别名与接口的区别
4.2.1 类型别名
类型别名可以用来给一个类型起一个新名字,常用于联合类型或复杂类型。
type StringOrNumber = string | number;
let value: StringOrNumber;
value = "Hello"; // 合法
value = 42; // 合法
4.2.2 接口
接口主要用于描述对象的结构,支持扩展和实现。
interface Person {
name: string;
age: number;
}
interface Student extends Person {
grade: number;
}
let student: Student = {
name: "李四",
age: 18,
grade: 90
};
4.2.3 区别
-
类型别名:可以定义基本类型、联合类型、交叉类型等,但不能被类实现。
-
接口:主要用于描述对象的结构,支持扩展和实现。
4.3 类型推断与类型断言
4.3.1 类型推断
TypeScript 会根据变量的赋值自动推断其类型。
let num = 42; // TypeScript 推断 num 为 number 类型
num = "Hello"; // 报错,num 是 number 类型
4.3.2 类型断言
类型断言用于告诉编译器某个值的类型。
4.4 泛型约束
泛型约束用于限制泛型的类型范围。
interface Lengthwise {
length: number;
}
function logLength<T extends Lengthwise>(arg: T): void {
console.log(arg.length);
}
logLength("Hello"); // 5
logLength([1, 2, 3]); // 3
// logLength(42); // 报错,number 没有 length 属性
4.5 映射类型
映射类型允许基于旧类型创建新类型。
type Readonly<T> = {
readonly [P in keyof T]: T[P];
}
interface Person {
name: string;
age: number;
}
type ReadonlyPerson = Readonly<Person>;
let person: ReadonlyPerson = {
name: "张三",
age: 20
};
// person.name = "李四"; // 报错,name 是只读属性
4.6 条件类型
条件类型用于根据条件选择类型。
type IsString<T> = T extends string ? true : false;
type A = IsString<"Hello">; // true
type B = IsString<42>; // false
4.7 索引类型
索引类型允许通过索引访问对象的属性类型。
interface Person {
name: string;
age: number;
}
type NameType = Person["name"]; // string
type AgeType = Person["age"]; // number
4.8 装饰器
装饰器是一种特殊类型的声明,可以附加到类、方法、属性或参数上,用于修改类的行为。
function log(target: any, key: string, descriptor: PropertyDescriptor) {
const originalMethod = descriptor.value;
descriptor.value = function (...args: any[]) {
console.log(`调用方法: ${key}`);
return originalMethod.apply(this, args);
};
return descriptor;
}
class Calculator {
@log
add(a: number, b: number): number {
return a + b;
}
}
const calc = new Calculator();
calc.add(2, 3); // 调用方法: add
4.9 命名空间
命名空间用于组织代码,避免全局命名冲突。
namespace MathUtils {
export function add(a: number, b: number): number {
return a + b;
}
export function subtract(a: number, b: number): number {
return a - b;
}
}
console.log(MathUtils.add(2, 3)); // 5
console.log(MathUtils.subtract(5, 3)); // 2
4.10 模块化
TypeScript 支持 ES6 模块化语法,可以将代码拆分为多个模块。
// math.ts
export function add(a: number, b: number): number {
return a + b;
}
// main.ts
import { add } from './math';
console.log(add(2, 3)); // 5
五、总结
TypeScript 的进阶知识点包括联合类型、交叉类型、类型别名、泛型约束、映射类型、条件类型、索引类型、装饰器、命名空间和模块化等。这些知识点能够帮助我们更好地组织代码、提升代码的可维护性和可扩展性。通过掌握这些进阶特性,您可以编写出更加健壮和灵活的 TypeScript 代码。
希望这份整理对你有帮助!如果需要进一步细化某部分内容,可以告诉我! 😊