摘要:阿里前端筆試題,題目不多,難度也不大,我只記錄了兩道稍微有點難度的編程題。題目如下的功能是,將一個字面量對象轉化為一個格式的字符串。
阿里前端筆試題,題目不多,難度也不大,我只記錄了兩道稍微有點難度的編程題。題目如下:
1.JSON.stringify 的功能是,將一個 JavaScript 字面量對象轉化為一個 JSON 格式的字符串。例如:
const obj = {a:1, b:2} JSON.stringify(obj) // => "{"a":1,"b":2}"
當要轉化的對象有“環”存在時(子節點屬性賦值了父節點的引用),為了避免死循環,JSON.stringify 會拋出異常,例如:
const obj = { foo: { name: "foo", bar: { name: "bar" baz: { name: "baz", aChild: null // 待會將指向obj.bar } } } } obj.foo.bar.baz.aChild = obj.foo // foo->bar->baz->aChild->foo形成環 JSON.stringify(obj) // => TypeError: Converting circular personucture to JSON
請完善以下“環”檢查器函數 cycleDetector,當入參對象中有環時返回 true,否則返回 false。
function cycleDetector(obj) { // 請添加代碼 }
解題思路:首先很容易想到要遍歷這個對象,然后判斷屬性值是否為一個對象,如果是,則遞歸遍歷這個屬性值,但難點是該如何判斷這個屬性值是否為某個父節點的引用,要怎樣拿到父節點的引用呢???
其實我們可以先用一個數組cache用來保存對象類型的屬性值,再用一個標記變量來標記是否有環,然后遍歷時判斷這個屬性值類型是否為一個對象,如果是,則判斷這個屬性值是否在那個cache數組里,如果在,則表明有環,如果不在,則把這個屬性值添加到數組里,再遞歸遍歷這個屬性值即可。
具體代碼如下:
function cycleDetector(obj) { let hasCircle = false, //用一個變量去標記是否有環 cache = []; //保存值為對象的屬性值 (function(obj) { Object.keys(obj).forEach(key => { const value = obj[key] if (typeof value == "object" && value !== null) { const index = cache.indexOf(value) if (index !== -1) { //如果cache中存在這個value,則表示有環 hasCircle = true return } else { cache.push(value) arguments.callee(value) } } }) })(obj) return hasCircle }
2.實現一個EventEmitter類,這個類包含以下方法:
on(監聽事件,該事件可以被觸發多次)
once(也是監聽事件,但只能被觸發一次)
fire(觸發指定的事件)
off(移除指定事件的某個回調方法或者所有回調方法)
class EventEmitter { /**請補充你的代碼***/ } const event = new EventEmitter() const drank = (person) => { console.log(person + "喝水") } event.on("drank", drank) event.on("eat", (person) => { console.log(person + "吃東西") }) event.once("buy", (person) => { console.log(person + "買東西") }) event.fire("drank", "我") // 我喝水 event.fire("drank", "我") // 我喝水 event.fire("eat", "其它人") // 其它人吃東西 event.fire("eat", "其它人") // 其它人吃東西 event.fire("buy", "其它人") //其它人買東西 event.fire("buy", "其它人") //這里不會再次觸發buy事件,因為once只能觸發一次 event.off("eat") //移除eat事件 event.fire("eat", "其它人") //這里不會觸發eat事件,因為已經移除了
解題思路:這題其實就是實現發布-訂閱模式了,難點在于怎樣實現once事件,即只觸發一次。其實也就是要實現兩種類型的事件,我們可以用不同的對象去保存這兩種類型的事件,然后在fire的時候,這兩種事件都要被處理即可。
具體代碼如下:
class EventEmitter { constructor() { this.queue = {} //可觸發多次的事件 this.onceQueue = {} //只能觸發一次的事件 } on(event, fn) { //監聽事件,可以觸發多次 if (!this.queue[event]) this.queue[event] = [] this.queue[event].push(fn) } once(event, fn) { //監聽事件,只能觸發一次 if (!this.onceQueue[event]) { this.onceQueue[event] = { fns: [], hasFired: false } } this.onceQueue[event].fns.push(fn) } fire() { //觸發指定的事件 const event = [].shift.call(arguments), //取得事件名稱 fns = this.queue[event], //取得該事件里所有的回調函數(可以觸發多次的事件) onceFns = this.onceQueue[event] //取得該事件里所有的回調函數(只能觸發一次的事件) if (fns && fns.length != 0) { let i = 0,fn while (fn = fns[i++]) { fn.apply(this, arguments) } } if (onceFns && !onceFns.hasFired) { let i = 0,fn while (fn = onceFns.fns[i++]) { fn.apply(this, arguments) } this.onceQueue[event].hasFired = true } } off(event, fn = null) { //可移除特定事件里的某個回調函數或者所有回調函數 const fns = this.queue[event] if (!fns || fns.length == 0) return if (fn) { //移除該事件特定的回調 this.queue[event] = fns.filter(item => { return item !== fn }) } else { //移除該事件所有的回調 this.queue[event] = [] } } }
原文地址:https://lenshen.com/2017/08/2...
最后,我的github:https://github.com/lensh
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/84928.html
摘要:順便一說,這首歌的原唱是秋田,中島當年嗓子壞了,才有這歌。中文是直接翻譯來的,作曲是秋田。一部電影春夏秋冬又一春春夏秋冬又一春是由金基德執導,金英民吳英秀金基德主演的一部韓國電影。年月日于韓國上映。 原鏈接: http://bluezhan.me/weekly/#/9-2 1、web前端 Angular vs. React vs. Vue: A 2017 comparison 9 S...
摘要:順便一說,這首歌的原唱是秋田,中島當年嗓子壞了,才有這歌。中文是直接翻譯來的,作曲是秋田。一部電影春夏秋冬又一春春夏秋冬又一春是由金基德執導,金英民吳英秀金基德主演的一部韓國電影。年月日于韓國上映。 原鏈接: http://bluezhan.me/weekly/#/9-2 1、web前端 Angular vs. React vs. Vue: A 2017 comparison 9 S...
摘要:前端日報精選譯中一些超級好用的內置方法漫談組件庫開發一多層嵌套彈層組件高階組件淺析的工廠函數打包優化之速度篇中文教程用純實現跳跳球動畫眾成翻譯個幫助你學習的快速且久經考驗的技巧眾成翻譯自定義屬性使用進行動態更改眾成翻譯真假值知多 2017-08-26 前端日報 精選 【譯】ES6中一些超!級!好!用!的內置方法漫談 React 組件庫開發(一):多層嵌套彈層組件React 高階組件淺析...
摘要:背景個人背景就讀于東北某普通二本院校計算機軟件工程專業,現大四,北京實習前端方向,自學,技術棧時間背景大概是在月日準備好簡歷開始投遞秋招差不多已經結束招聘崗位不多,投遞對象為大一些的互聯網公司事件背景第一個入職的是好未來的前端實習崗,待遇工 背景 個人背景 就讀于東北某普通二本院校計算機軟件工程專業,現大四,北京實習 前端方向,自學,vue技術棧 時間背景 大概是在11月9日準備...
閱讀 2909·2021-11-17 09:33
閱讀 1630·2021-10-12 10:13
閱讀 2425·2021-09-22 15:48
閱讀 2313·2019-08-29 17:19
閱讀 2587·2019-08-26 11:50
閱讀 1565·2019-08-26 10:37
閱讀 1732·2019-08-23 16:54
閱讀 2917·2019-08-23 14:14