本篇内容也来源于拉勾教育的学习,以及自己的一些扩展
使用ts的好处
语言
类型安全:强弱类型 -> 老师认为是否允许类型的隐式转换来判断强弱,强的不允许
类型检查:静态类型和动态类型->是否允许随意地修改变量类型
js毫无疑问地是弱类型/动态语言
弱类型问题:
1、运行时才报错
2、返回值不符合预期,改变函数功能 sum(100, '100') -> '100100'
3、对象索引的错误引用 obj: {[true]: 1}; obj['true']也可以引用到这个属性
强类型问题
1、更早的发现问题
2、代码更智能,编码更准确
3、重构更牢靠
4、减少类型判断
ts学习知识
装饰器原理:装饰器本身就是函数
//类装饰器表达式会在运行时当作函数被调用,类的构造函数作为其唯一的参数(必须放在class上面,其作用是在传入的类的构造函数的原型上加方法 属性)
function log(target: Function) {
//target是构造函数
console.log(target === Foo); //true
target.prototype.log = function() {
console.log(this.bar)
}
}
//方法装饰器有三个参数:1-实例(装饰的类输出的实例),2-方法名,3-descriptor描述符对象
funciotn dong(target: any, name: string, descriptor: any) {
console.log(target, name, descriptor);
//这里通过修改descriptor.value扩展了bar方法
const biz = descriptor.value;
descriptor.value = function (val: string) {
console.log('dong');
//原始逻辑
biz.call(this, val)
}
}
//属性装饰器,接收两个参数:1-实例,2-属性名称
funtion mua1 (target, name) {
target[name] = 'mua1';
}
funtion mua2(option: string) {
//返回的才是装饰器函数
return function(target, name) {
target[name] = option
}
}
//形参装饰器
@log
class Foo {
bar = 'bar';
@mua1
a!: string;
@mua2('mua2') //()运算符优先级高于@
b!: string;
@dong
setBar (val: string) {
this.bar = val;
}
}
ts的泛型可以看作js的函数,主要目的是为了复用,也可以做类型推导。
const s = [() => 1, () => 's'] as const;
type S = typeof s;
type M<T extends ReadonlyArray<() => any>> = {
-readonly [key in keyof T]: T[key] extends () => any ? ReturnType<T[key]> : never;
}
type R = M<S>; //type R = [number, string]
//infer 类型抽取!!!
const a = [
{label: '22', value: 2},
{label: '33', value: 3}
];
type arr = typeof a;
interface zz {
ff: number;
}
type getArrItem<T> = T extends Array<infer P> ? P : T;
type item = getArrItem<arr>;//{label: string, value: number}
type item1 = getArrItem<zz>;
ts工具函数
ts+vue
UI库等第三方库引入声明文件
//常用库都是有声明文件的,如果没有就手动安装
//安装地址形式通常是@types/xxx 也就是npm i -D @type/xxx
this.$ref 使用@Ref装饰器 第三方库的类型,未知的要学会查官方文档,不要懒,不要做一条懒狗,偷用any
路由和Vuex
组件路由守卫:
创建App.vue时,因为其他组件都没创建,在这做配置后,其他组件通过@Component做修饰时,Component装饰器已经变了,
所以可以在App.Vue创建Component前通过Component.registerHooks([])注册生命周期钩子,
比如Component.registerHooks([beforeRouteEnter]);
这样在所有组件中就可以像使用mounted一样使用beforeRouteEnter钩子了
vuex整合推荐vuex-class