1. 语言类型
1.1 强类型与弱类型
强类型不允许随意的隐式类型转换,而弱类型是允许的
强类型和弱类型区别是是否允许随意的隐式转换
强类型是语法层面限制类型,如果类型不对,编译阶段就会报错。而js只能在运行阶段通过类型判断去限制。这也就意味着JS只能到代码运行到这一行时才能发现错误,不能像其它语言编译阶段就可以发现错误
强类型优势:
- 更早发现错误(编译阶段就可发现错误,不用等到代码运行)
- 代码更智能,编码更准确
- 重构更牢靠
- 减少不必要的类型判断
1.2 静态类型与动态类型
静态类型:一个变量声明时它的类型就是明确的,声明过后,它的类型就不允许再修改
动态类型:运行阶段才能够明确变量类型,而且变量类型随时可变
静态类型与动态类型区别是是否允许随时修改变量类型
image.png
JS是弱类型,动态类型
2. TS简介
下面这张图可以让我们充分的理解什么是TS
image.png
3. TS环境配置
3.1 生成ts配置文件
tsc --init
3.2 将报错信息设置为中文
tsc --locale zh-CN
vs code中在设置里搜索typescript locale
,改为中文即可
4. ts的几种数据类型
const a: string = "foobar";
const b: number = 100; // NaN Infinity
const c: boolean = true;
// const d: boolean = null;
const e: void = undefined; // 非严格模式下也可以赋值null, 严格模式下只能赋值undefined
const f: null = null;
const g: undefined = undefined;
const h: symbol = Symbol(); // es5中不能使用Symbol(),包括es6中的Promise等, 解决办法,在配置文件中添加"lib": ["es2015", "DOM"], DOM是默认的的,不开启lib时默认就有
5. 定义类型
5.1 object
ts中的object包括{}, [], function
const foo: object = {} // [] // function() {}
但是如果仅仅想声明对象,需要使用对象字面量语法
const obj: {} = {};
5.2 array
const arr1: Array<number> = [1, 2];
const arr2: number[] = [1, 2, 3];
5.3 元组
元组是明确元素数量与元素类型的数组
常见用于函数返回值
5.4 枚举
常见用于用某几个数值代表某种状态
let state = 0; // 0, 1, 2三种状态
enum PostStatus {
Draft, // = 0
UnPublished, // = 1
Published, // = 2
}
// 编译后
(function (PostStatus) {
PostStatus[PostStatus["Draft"] = 0] = "Draft";
PostStatus[PostStatus["UnPublished"] = 1] = "UnPublished";
PostStatus[PostStatus["Published"] = 2] = "Published";
})(PostStatus || (PostStatus = {}));
如果是字符串枚举,因为无法自增,所以就必须给每一个成员手动添加值
enum PostStatus {
Draft = 'aaa'
UnPublished = 'bbb'
Published = 'ccc'
}
枚举会侵入代码,建议使用常量枚举,即在枚举前加const
const enum PostStatus {
Draft, // = 0
UnPublished, // = 1
Published, // = 2
}
5.5 函数
- 函数声明
行参和实参数量必须相等
function func1(a: number, b: number): string {
return 'str'
}
func1(100, 200)
- 可选参数
function func2(a: number, b?: number): string {
return "str";
}
// 或者使用默认参数
function func3(a: number, b: number = 10): string {
return "str";
}
- 传入多个参数
function func4(a: number, b: number, ...rest: number[]): string {
return "str";
}
- 函数表达式
const func5: (a: number, b: number, ...rest: number[]) => string = function (
a: number,
b: number
): string {
return "str";
};
6. any(任意参数)
6.1 隐式类型推断
let age = 10; // 隐式推断为number类型
age = "str"; // 赋值string类型时报错
let foo; // 声明并未赋值,此时推断为any类型,下面先赋值number,再赋值string,也不会报错
bar = 10; // any
bar = "str"; // any
6.2 类型断言
类型断言有as
或者<>
,<>
在jxs语法中会和标签产生冲突,所以推荐使用as
const nums = [100, 200, 300, 400];
const res = nums.find((i) => i > 0);
const num1 = res as number;
const num2 = <number>res;
7. 接口
7.1 只读 readonly
7.2 动态属性
如果不确定有几个值,可以用以下方法
interface cache {
[key: string]: string
}
8. 类
最新的语法中,不再在construction
通过this来动态添加属性,而是在外面对每个属性声明
// 如果没有在外部设置属性值,那就要在construction中设置属性值
class Person {
name: string = "init name"
age: number
constructor(name: string, age: number) {
this.name = name // 不再直接通过this来动态添加属性,而是需要在外面声明
this.age = age
}
}
8.1 修饰符
public
private
protected(可以在子类获取,外部获取不到)
注意:如果给constructor设置了private,那么外部就不能实例化了,但是内部可以访问到,所以这是我们在内部加一个静态方法,去返回实例
class Student extends Person {
private constructor(name: string, age: number) {
super(name, age)
console.log(this.gender)
}
static create(name: string, age: number) {
return new Student(name, age)
}
}
const jack = Student.create("jack", 18)
console.log(jack.name)
console.log(jack.age)
console.log(jack.gender)
8.2 只读属性readonly
8.3 类与接口
接口仅定义公共能力,而不做具体方法实现,建议一个接口只实现一个功能
interface Eat {
eat(food: string): void
}
interface Run {
run(distance: number): void
}
class Person implements Eat, Run {
eat(food: string): void {
console.log(`优雅的进餐,${food}`)
}
run(distance: number): void {
console.log(`直立行走:${distance}`)
}
}
class Animal implements Eat, Run {
eat(food: string): void {
console.log(`呼噜呼噜的吃,${food}`)
}
run(distance: number): void {
console.log(`爬行:${distance}`)
}
}
8.4 抽象类
与接口类似,如果比较复杂的类建议使用抽象类
注意:抽象类无法new,只能继承
abstract class Animal {
eat(food: string): void {
console.log(`呼噜呼噜的吃,${food}`)
}
abstract run(distance: number): void
}
class Dog extends Animal {
run(distance: number): void {
console.log(`爬行:${distance}`)
}
}
9. 泛型
function createNumberArray(length: number, value: number): number[] {
const arr = Array<number>(length).fill(value)
return arr
}
function createStringArray(length: number, value: string): string[] {
const arr = Array<string>(length).fill(value)
return arr
}
function createArray<T>(length: number, value: T): T[] {
const arr = Array<T>(length).fill(value)
return arr
}
const resResult = createArray<string>(3, "foo")
10. 类型声明
如果一个成员在定义时没有声明类型,那么在使用时可以为他声明类型
import { camelCase } from 'lodash'
declare function camelCase(input: string): string
const res = camelCase('hello typed')
一般第三方库都有单独的类型声明模块,例如lodash的声明模块@types/lodash
网友评论