npm -g install ts-node typescript
1、number类型
- // 先定义 后给值
- let a: number;
- a = 10;
-
- // 定义类型 直接给值
- let a: number = 10;
-
- // 声明不给类型直接给值, 给什么值就是什么类型
- let a = 10
2、boolean类型
let a: boolean = false
3、声明不给类型直接给值 给什么值就是什么类型
let a = false; // 类型为boolean
4、使用字面量进行类型声明
- let a: 10;
- a = 10;
- a = 11; // 报错
-
- //联合类型
- let b: 1 | 2;
- b = 1;
- b = 2;
- b = 3; // 报错 b的值只能是1和2
-
- // c的类型可以是boolean、string两种类型
- let c: boolean | string;
5.、any任意类型
- let d: any; // 显示声明any类型
- d = 10;
- d = 'hello';
- d = true;
-
- let a; // 隐式any
6、unknown表示未知类型的值
- let e: unknown;
- e = 10;
- e = 'hello';
- e = true;
-
- let d: any;
- s = d; // d是类型是any,它可以赋值给任意类型
未知类型不可以给已知的类型变量赋值
- let e: unknown;
- let s: string;
- s = e; // 报错e的类型是未知类型 而s是字符串类型
-
- // 解决办法
- 方法一:if判断一下
- if(typeof e === 'string'){
- s = e
- }
-
- 方法二:类型断言(用来告诉解析器变量的实际类型)
- s = e as string
- //或
- s =
e;
7、void用来表示空(用函数为例 , 表示没有返回值)
- function fn(): void {
- return 或 return undefine 或 returnfine
- }
8、never 表示永远不会有返回结果
- function fn2(): never {
- throw new Error('报错了')
- }
9、object
- let a: object;
- a = {}
- a = function() {}
10、在属性名后上加?表示可选
- let b: { name: string, age?: number }
- b = { name: '郑建', age: 18}
- b = { name: '郑建'}
11、[propName: string]: any(表示任意类型的属性)
- let c: {name: string, [propName: string]: any};
- c = { name: '郑建', age: 18, gender: '男' }
12.数组声明
- // 类型[]
- // Array<类型>
-
- // string[]表示数组里面的元素都是string类型
- let e: string[];
- e = ['a', 'b', 'c']
-
- // Array
表示数组里面的元素都是数字 - let g: Array
; - g = [1, 2, 3]
13、元组类型 (就是不可变的数组)
- let h: [string, string];
- h = ['hello', 'a']
14、enum枚举
- enum Gender {
- male = 0,
- female = 1,
- }
-
- let i: { name: string, gender: Gender }
-
- i = {
- name: '郑建',
- gender: Gender.male
- }
-
- console.log(i.gender === Gender.male);
15、类型别名
- type myType = 1 | 2 | 3 | 4;
- let k: myType;
- k = 6; //报错 k的值只能是1 2 3 4
声明变量的时候,我们推荐是用let和const,而不推荐var,并加上类型说明,且作用域为块级即以{}为界。
- let lang: string = 'hello world';//如果省略类型说明,TS也可进行自动推断
- lang = 2022; //赋值错误! 如果需要可以使用联合类型:let lang: number | string = 'TS';
- let age: number = 20;
-
- const num: number = 6.66666;//num以后不可改变,只可以读取,类似常量
- num = 3.14; //错误
将对象、数组中的元素拆分到指定变量中,以方便使用。
- //解构数组
- let array = [1, 2, 3, 4];
- let [one, two] = array; //注意使用[]
- console.log(one); // 1
- console.log(two); // 2
- let [first, ...others] = array; //剩余变量。...others是一个可变长度的数组
- console.log(...others); // 2 3 4
- //...是一个展开运算符
- let newArr = [0, ...others, 5];
- console.log(newArr); // 0 1 2 3 4 5
-
- //解构对象
- let People = {
- name: "xiaoyi",
- age: 20,
- sex: "male"
- };
- let {name, age} = People;//注意使用{},且变量名需与对象中道属性名一致
- console.log(name, age); // xiaoyi 20
1、需要使用完整函数类型定义。
-
- //命名函数,有完整的参数和返回类型。可以不用,TS将自动进行类型推断但推荐使用!
- function sum(x: number, y: number): number {
- return x + y;
- }
- //匿名函数
- let res_sum = function(x: number, y: number): number { return x + y; };
- console.log(sum(1, '2')); //参数类型必须和形参的类型一致
- console.log(sum(1)); //参数个数必须和函数的形参个数一致
- console.log(typeof sum(1, 2)); //打印出函数的返回值类型
2、可选参数
- //可选参数,必须放在必要参数后
- function greeting(firstName: string, lastName?: string) {
- if(lastName) { //判断lastname是否有值传进来
- return `Hello ${firstName} ${lastName}!`; //使用模板字符串进行拼接
- }
- return `Hello ${firstName}!`;
- }
- console.log(greeting('周'));
- console.log(greeting('周', '晓忆'));
- console.log(greeting('周', '晓忆', '你好')); //参数个数 !== 函数的形参个数不一致,产生错误。
-
3、默认参数【有缺省值】
- //默认参数,不必在必要参数后
- function greeting(firstName: string, lastName = 'yinjie') {
- return `Hello ${firstName} ${lastName}!`;
- }
- console.log(greeting('zhou'));
- console.log(greeting('zhou', 'xiaoyi'));
- console.log(greeting('zhou', 'xiaoyi', 'Yong'));//参数个数 !== 函数的形参个数不一样发生错误!
-
4、不定长参数
- //剩余参数,会被当做个数不限的可选参数。可以一个都没有,也可以有任意个
- function greeting(firstName: string, ...restName: string[]) {//...代表的是一个可变长度的数组
- return `Hello ${firstName} ${restName.join(' ')}!`;
- }
- console.log(greeting('zhou', 'wang', 'li', 'liu', 'guan', 'zhang', 'qin'));
- console.log(greeting('zhou'));
-
5、箭头函数
特点:简化函数定义、解决this问题。但是可读性比较差。
- // 无参数,函数体代码只有一行,则该行结果即为函数返回值
- let greeting1 = () => `Hello TS!`; // return可以省略
- console.log(greeting1()); // Hello TS!
-
- // 一个参数,函数体代码只有一行,则该行结果即为函数返回值
- let greeting2 = (name: string) => `Hello ${name}`; // return可以省略
- console.log(greeting2('QiGe')); // Hello QiGe
-
- //两个及以上的参数,函数体代码只有一行,则该行结果即为函数返回值
- let add1 = (n1: number, n2: number) => n1 + n2;
- console.log(add1(1, 2)); // 3
-
- //两个及以上的参数,函数体代码多于一行,则必须用{}包裹,且显式给出return
- let add2 = (n1: number, n2: number) => {
- let sum = n1 + n2;
- return sum;//改为sum++结果如何?
- }
- console.log(add2(1, 2)); // 3
-
类是属性和函数的集合,是生成对象(Object)或类实例的模板。
1、类的定义和使用
关键字get 定义方法: 这个方法用于只读属性的,不可修改属性
关键字set定义方法: 这个方法用于修改属性是
readonly定义属性: readonly使其只能在初始化时赋值,以后不可更改
- // getter和setter
- class People { // class是关键字,类名默认全部大写首字母
- private readonly _name: string; // 私有属性,外部不可访问。readonly使其只能在初始化时赋值,以后不可更改。
- private _sex: string; // 私有属性,习惯以_开头进行命名
-
- constructor(name: string, sex: string){ // 构造函数,一般用于初始化
- this._name = name;
- this._sex = sex;
- }
- get name(): string {
- return this._name;
- }
- set name(value: string) { // 错误! _name有readonly属性,不可以被修改
- this._name = value;
- }
- get sex(): string {
- return this._sex;
- }
- set weather(sex: string) {
- this._sex = sex;
- }
- }
-
- let people = new People('zhouxiaoyi', 'male'); // 使用new关键字生成对象
- console.log(people.name, people.weather);
- people.weather = 'sunny'; // OK
- people.name = 'Wang'; // 只读属性,不可以被修改
- console.log(people);
-
2、静态属性
类中的属性或函数有static修饰,则可直接使用而不需要实例化
- // 静态属性,内建或自定义,无需new即可使用,可以直接通过类名进行访问
- // Math是一个包装类,自带的,里面的所有方法都是静态的。
- console.log(Math.round(89.64)); // 90
- console.log(Math.pow(2, 8)); // 256
- class Tool {
- static title = 'box';
- static printInfo() {
- console.log('The box can contain pens!');
- }
- }
- // 静态方法与静态函数可以直接通过类名直接访问。
- console.log(Tool.title);
- Tool.printInfo();
-
3、继承
面向对象有三大特性:封装、继承、多态。
可以通过extends关键字继承其它类,从而成为其子类。
- class Animal {
- // 当构造函数传入的参数加上了“访问权限控制符”,则同时会声明同名类属性,并赋值
- constructor(public name: string) { }
- protected log(message: string) {
- console.log(message);
- }
- move(distanceInMeters: number = 0) {
- this.log(`${this.name} moved ${distanceInMeters}m.`); // 请注意name来自何处
- this.log('==============');
- }
- }
-
- class Horse extends Animal {
- constructor(name: string) {
- // 这里创建了构造函数 必须要调用父亲的构造器 通过super
- super(name); // 通过super调用父类构造器
- }
- run(distanceInMeters = 50) { // 自己独有的函数
- this.log("Clop, clop...");
- super.move(distanceInMeters); // 通过super调用父类方法
- }
- }
-
- class Eagle extends Animal {
- constructor(name: string) { super(name); }
- reborn() { // 自己独有的函数
- console.log('Reborn? It is a joke, hahaha!');
- }
-
- }
-
- let tom: Horse = new Horse("Tommy the Palomino");
- tom.run(8964);
- let sam: Eagle = new Eagle("Sammy the Hawk");
- sam.move(1024); // sam的move函数来自何处?
- sam.reborn();
我们经常说的模块化开发、组件化开发、工程化开发但是有些人可能对这种词比较陌生,下面我来说说,
模块化:模块化, 首先先知道模块是什么? 模块就是一个js文件,那模块化就是我们写的东西都放在一个一个js文件里,比如说公共的js逻辑代码 我们写好放到一个js里, 我们哪个页面需要的话就引入这个模块,这就是我理解的模块化开发,实现代码的复用 降低代码冗余、提高开发效率和降低开发成本。
组件化: 一个页面可以分为很多很多的小组件,每个组件都有自己要实现的功能,而且有些组件可以多个页面的复用,需要就引入进来 ,这就是组件化开发
工程化:工程化就好比厂里的流水线,一套流程下来该有的东西都给你安装上,不需要不一个一个依赖的引入,这个创建项目的时候用到比如 用vite创建项目 或则webpack创建项目