Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ts #76

Open
XJIANBIN opened this issue Feb 18, 2022 · 0 comments
Open

ts #76

XJIANBIN opened this issue Feb 18, 2022 · 0 comments

Comments

@XJIANBIN
Copy link
Owner

point

  • type 用来定义,比如定义联合类型
type Combinable = string | number
  • Tuple

元组类型只能表示一个已知元素数量和类型的数组。

let x: [string, number]
  • 接口首字母大写,且赋值的时候,变量的形状必须和接口的形状保持一致。

  • 索引签名,用来实现定义任意属性

interface Person {
	name: string
	age?: number
	[propName: string]: any // 必须是确定属性和可选属性类型的父集
}

let tom: Person = {
	name: 'Tom',
	gender: 'male',
}
  • 绕开额外属性检查的方式
// 1鸭式辨型法
// 在函数参数里写对象相当于直接给labelObj赋值,通过用一个变量myObj接受对象,myObj不会经过额外属性检查,把他赋值给labelObj,根据类型的兼容性,两种对象都有label属性,可以用这种方式来绕过多余的类型检查
interface LabeledValue {
	label: string
}
function printLabel(labeledObj: LabeledValue) {
	console.log(labeledObj.label)
}
let myObj = { size: 10, label: 'Size 10 Object' }
printLabel(myObj) // OK
// 类型断言
interface Props {
	name: string
	age: number
	money?: number
}

let p: Props = {
	name: '兔神',
	age: 25,
	money: -100000,
	girl: false,
} as Props // OK
// 索引签名
interface Props {
	name: string
	age: number
	money?: number
	[key: string]: any
}

let p: Props = {
	name: '兔神',
	age: 25,
	money: -100000,
	girl: false,
} // OK
  • 接口可以定义多次,会被自动合并为单个接口,类型别名不可以
  • 接口的扩展就是继承,通过 extends 实现,类型别名的扩展就是交叉类型,通过&来实现。
interface PointX {
	x: number
}

interface Point extends PointX {
	y: number
}

type PointX = {
	x: number
}

type Point = PointX & {
	y: number
}
  • 泛型约束
interface Sizeable {
	size: number
}
function trace<T extends Sizeable>(arg: T): T {
	console.log(arg.size)
	return arg
}
  • 泛型工具类型
    1 typeof
    2 keyof
interface Person {
	name: string
	age: number
}

type K1 = keyof Person // "name" | "age"
type K2 = keyof Person[] // "length" | "toString" | "pop" | "push" | "concat" | "join"
type K3 = keyof { [x: string]: Person } // string | number
//
function prop<T extends object, K extends keyof T>(obj: T, key: K) {
	return obj[key]
}
  • 3 in 遍历枚举类型
	tyoe Keys= 'a' | 'b' | 'c'
	type Obj = {
		[p in Keys] : any
	}
  • 4 infer

  • 5 extends

  • 6 类型索引

  • 7 Readonly

  • 8 Partial, Partial 只支持处理第一层属性

  • 9 DeepPartial

  • 10 Required

  • 11 Pick

  • 12 Record
    Record<K extends keyof any, T> 的作用是将 K 中所有的属性的值转化为 T 类型。

type Record<K extends keyof any, T> = {
	[P in K]: T
}
type Pick<T, K extends keyof T> = {
	[P in K]: T[P]
}

interface Todo {
	title: string
	description: string
	completed: boolean
}

type TodoPreview = Pick<Todo, 'title' | 'completed'>

const todo: TodoPreview = {
	title: 'Clean room',
	completed: false,
}

Question

1 为什么 TS 的函数表达式得这样写

let mySum: (x: number, y: number) => number = function (x: number, y: number): number {
	return x + y
}

2 采用函数表达式接口定义函数的方式时,对等号左侧进行类型限制,可以保证以后对函数名赋值时保证参数个数、参数类型、返回值类型不变。

interface SearchFunc {
	(source: string, subString: string): boolean
}

3 infer 代码不懂

type ReturnType<T> = T extends (...args: any[]) => infer R ? R : any
//以上代码中 infer R 就是声明一个变量来承载传入函数签名的返回值类型,简单说就是用它取到函数返回值的类型方便之后使用。

5 DeepPartial

type DeepPartial<T> = {
     // 如果是 object,则递归类型
    [U in keyof T]?: T[U] extends object
      ? DeepPartial<T[U]>
      : T[U]
};

type PartialedWindow = DeepPartial<T>; // 现在T上所有属性都变成了可选啦

6 Required 将类型的属性变成必选

function getValues<T, K extends keyof T>(person: T, keys: K[]): T[K][] {
	return keys.map((key) => person[key])
}

interface Person {
	name: string
	age: number
}

const person: Person = {
	name: 'musion',
	age: 35,
}

getValues(person, ['name']) // ['musion']
getValues(person, ['gender']) // 报错:
// Argument of Type '"gender"[]' is not assignable to parameter of type '("name" | "age")[]'.
// Type "gender" is not assignable to type "name" | "age".

// T[K]表示对象T的属性K所表示的类型,在上述例子中,T[K][] 表示变量T取属性K的值的数组

// 通过[]索引类型访问操作符, 我们就能得到某个索引的类型
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant