本文簡介 本文主要講解使用 NodeJS 操作 Redis ,順便會先帶一帶 Redis 基礎用法。 在寫本文時,使用 NPM 安裝的 Redis 依賴包已經到了 4.1.0 版本了。我以前用過 2.8 ,這兩個版本在用法上也是有差別的。可能一些老項目還在用老版本的依賴包。所以我會把2個版本的用法都 ...
前端面試高頻筆試題,前端面試要做到提前準備提前練習,刷一定的面試題筆試題量,面試才能事半功倍一路暢通。
1. 實現快速排序
var arr = [9, 4, 3, 1, 6, 3, 8, 7]
/**
* 快速排序
* @param {array} arr 需要排序的數組
* @returns {array}
*/
function quickSort (arr) {
if (arr.length <= 1) return arr
var arr1 = [], arr2 = []
for (var i = 1; i < arr.length; i++) {
if (arr[i] < arr[0]) {
arr1.push(arr[i])
} else {
arr2.push(arr[i])
}
}
arr1 = quickSort(arr1)
arr2 = quickSort(arr2)
arr1.push(arr[0])
return arr1.concat(arr2)
}
console.log(quickSort(arr)) // [1, 3, 3, 4, 6, 7, 8, 9]
步驟分析:
- 首先設定一個分界值,通過該分界值將數組分成左右兩部分。
- 將大於或等於分界值的數據集中到數組右邊,小於分界值的數據集中到數組的左邊。此時,左邊部分中各元素都小於分界值,而右邊部分中各元素都大於或等於分界值。
- 然後,左邊和右邊的數據可以獨立排序。對於左側的數組數據,又可以取一個分界值,將該部分數據分成左右兩部分,同樣在左邊放置較小值,右邊放置較大值。右側的數組數據也可以做類似處理。
- 重覆上述過程,可以看出,這是一個遞歸定義。通過遞歸將左側部分排好序後,再遞歸排好右側部分的順序。當左、右兩個部分各數據排序完成後,整個數組的排序也就完成了。
2. 實現 add(1)(2,3)(4,5,6) 的調用方式
function add(...args) {
var f = add.bind(null, ...args)
f.sum = () => {
return args.reduce((a, b) => a + b, 0)
}
return f
}
console.log(add(1)(2,3)(4,5,6).sum()) // 21
步驟分析:
- 使用 bind 返回新函數以保證滿足柯里化保留參數的特性
- 通過 reduce 進行值累加
3. 深拷貝
function clone (obj) {
if (obj === null || typeof obj !== 'object') return obj
// 處理數組和對象
if (obj instanceof Array || obj instanceof Object) {
var copy = obj instanceof Array ? [] : {}
for (let item in obj) {
copy[item] = clone(obj[item])
}
return copy
}
}
var data = {
a: 1,
b: [ 2, 3, 4 ],
c: {
d: 5
e: [ 6 ]
}
}
console.log(clone(data))
步驟分析:
- 判斷 obj 是否是值類型,如何是值類型直接返回
- 如果 obj 是數組或者對象,新建空對象
- 通過迴圈獲取到 obj 的值進行遞歸,結果賦給新建的空對象
- 該實現方式只實現了對象、值類型的拷貝,時間、方法等等可自行新增 if 進行創建賦值
4. 寫出這段程式的輸出內容
async function async1 () {
console.log('async1 start')
await async2()
console.log('async1 end')
}
async function async2 () {
console.log('async2')
}
console.log('script start')
setTimeout(function () {
console.log('setTimeout')
})
async1()
new Promise(function (resolve) {
console.log('promise1')
resolve()
}).then(function () {
console.log('promsise2')
})
console.log('script end')
輸出結果:
script start
async1 start
async2
promise1
script end
async1 end
promsise2
setTimeout
步驟分析:
- 首先,事件迴圈從巨集任務(macrostack)隊列開始,這個時候,巨集任務 (整體 script、setTimeout、setInterval) 隊列中,只有一個 script (整體代碼)任務 ()。
- 首先執行 console.log('script start'),輸出 'script start'
- 遇到 setTimeout 把 console.log('setTimeout') 放到 macrotask 隊列中
- 執行 aync1() 輸出 'async1 start' 和 'async2' ,把 console.log('async1 end') 放到 micro 隊列中
- 執行到 promise ,輸出 'promise1' ,把 console.log('promise2') 放到 micro 隊列中
- 執行 console.log('script end'),輸出 'script end'
- macrotask 執行完成會執行 microtask ,把 microtask quene 裡面的 microtask 全部拿出來一次性執行完,所以會輸出 'async1 end' 和 'promise2'
- 開始新一輪的事件迴圈,去除執行一個 macrotask 執行,所以會輸出 'setTimeout'