前端-每日一练

226 阅读2分钟

每天积累一点点,大厂offer抱回家!

1.使用 TypeScript 语法将没有层级的扁平数据转换成树形结构的数据

 const lists=[
     { id: 3, title: '子级2',parentId:1 },
     { id: 2, title: '子级1',parentId:1 },
     { id: 1, title: '父级1' },
     { id: 4, title: '父级2' },
     { id: 5, title: '子级3', parentId: 4 },
     { id: 6, title: '子级4', parentId: 5 },
 ]
 //拿到父级数组
 const list2 = lists.filter(it => !it.parentId && it.parentId !== 0)
 let res;
 //递归的方法
 const roback1 = (entity1: any, child: any) => { 
     entity1.forEach(it => { 
         //给it添加children属性
         it.children = [];
         let en=[];
         child.forEach(ch => { 
             if (ch.parentId && ch.parentId === it.id) { 
                 it.children.push(ch);
                 en.push(ch)
             }
         })
     //调用自身实现递归
     roback1(en,child)
     })
     res = entity1;
     
 }
 roback1(list2, lists)
 console.log(res)

2.模板解析

 const template = "嗨,{{ info.name.value }}您好,今天是星期{{ day.value }}"
 const data = {
     info: {
         name: {
             value: "张三",
         },
     },
     day: {
         value: "三",
     },
 }
 const render = function(template, data) {
     template = template.replace(/{{.*?}}/g, (item) => {
         let res = data
         const keyArr = item.match(/[a-zA-Z0-9]+/g)
         console.log(keyArr)
         keyArr.map((key) => {
             res = res[key]
         })
         return res
     })
     return template
 }
 console.log(render(template, data)) // 嗨,张三您好,今天是星期三

3.简单实现一个发布 / 订阅模式

 // 定义事件中心类
 class MyEvent {
     handlers = {} // 存放事件 map,发布者,存放订阅者
 ​
     $on(type, fn) {
         if (!Reflect.has(this.handlers, type)) {
             // 如果没有定义过该事件,初始化该订阅者列表
             this.handlers[type] = []
         }
         this.handlers[type].push(fn) // 存放订阅的消息
     }
 ​
     $emit(type, ...params) {
         if (!Reflect.has(this.handlers, type)) {
             // 如果没有该事件,抛出错误
             throw new Error(`未注册该事件${type}`)
         }
         this.handlers[type].forEach((fn) => {
             // 循环事件列表,执行每一个事件,相当于向订阅者发送消息
             fn(...params)
         })
     }
 ​
     $remove(type, fn) {
         if (!Reflect.has(this.handlers, type)) {
             throw new Error(`无效事件${type}`)
         }
         if (!fn) {
             // 如果没有传入方法,表示需要将该该类型的所有消息取消订阅
             return Reflect.deleteProperty(this.handlers, type)
         } else {
             const inx = this.handlers[type].findIndex(
                 (handler) => handler === fn
             )
             if (inx === -1) {
                 // 如果该事件不在事件列表中,则抛出错误
                 throw new Error("无效事件")
             }
             this.handlers[type].splice(inx, 1) // 从事件列表中删除该事件
             if (!this.handlers[type].length) {
                 // 如果该类事件列表中没有事件了,则删除该类事件
                 return Reflect.deleteProperty(this.handlers, type)
             }
         }
     }
 }

4.类数组和数组有什么区别?

const likeArr = { 0: "我", 1: "喜欢", 2: "你" }
const arr = ["我", "喜欢", "你"]
// 1.类数组没有length属性
console.log(likeArr.length) // undefined
console.log(arr.length) // 3
// 2.类数组没有来自Array.prototype上继承的方法,比如slice,map等等,至于其他的可以按F12,输入console.log(Array.prototype)进行查看
console.log(likeArr.slice) // undefined
console.log(arr.slice) // [Function: slice]
// 3.类数组的原型链上没有Array
//instanceof操作符,判断instanceof右边的Array的prototype原型是否在左边likeArr的原型链上
console.log(likeArr instanceof Array) // false
console.log(arr instanceof Array) // true

5.for in与Object.keys()的区别?

// for in 遍历可枚举属性和自身属性以及继承原型上的属性
// Object.keys 生成一个数组,由自身属性key组成的数组,不包括继承原型的属性
function Person(name, age) {
    this.name = name
    this.age = age
}
Person.prototype = {
    sex: "男",
}

var man = new Person("张三", 18)

console.log(Object.keys(man));//["name","age"]

for (var key in man) {
    console.log(key); //name age sex
}