題目:
給Array對象原型上添加一個sameStructureAs方法,該方法接收一個任意類型的參數,要求返回當前數組與傳入參數數組(假定是)相對應下標的元素類型是否一致。
假設已經寫好了Array.prototype.sameStructureAs ,會有下面的結果:
[1,1].sameStructureAs([2,2]) // true [1,[1,1]].sameStructureAs([2,[2,2]]) // true [1,[1]].sameStructureAs([[2],2]) // false [[],[]].sameStructureAs([[],[]]) // true
看到上面的代碼返回值,或許你就明白了。sameStructureAs方法的功能就如此之簡單。
那么, 該怎么實現呢,如下:
Array.prototype.sameStructureAs = function (other) { // Return 'true' if and only if 'other' has the same // nesting structure as 'this'. // Note: You are given a function isArray(o) that returns // whether its argument is an array. if (! (other instanceof Array) ) return false; // 傳入的不是數組返回false // 這個函數返回一個序列號 function count (arr) { // 第一次調用添加一個index屬性 if (typeof count.index === 'undefined') { count.index = 0 } var resStr = '' // 返回的序列號 if (!arr.length) resStr += count.index // 如果傳入數組為空,序列號為當前index屬性值 for (var i = 0; i < arr.length; i++) { if (typeof arr[i] !== 'object') { resStr += count.index // 如果這個元素不是數組,序列號為當前index屬性值 } else { count.index++ // 將index屬性值+1,是為了進入下一層數組 resStr += count(arr[i]) // 返回當前傳入數組的序列號 count.index-- //這里 -1 是回到當前層次中,繼續遍歷 } } return resStr } return count(this) === count(other) }
思路是這樣的:
因為這僅僅判斷數組,並沒有其他引用類型的對象,如RegExp、Date等,所以就容易多了。
我先設定數組第一層的非數組元素的序列號為0 ,也就是說 [1,1,1] 序列號是 [0,0,0],因此返回的數組序列號為'000',同樣[2,2,2]也返回'000'
每進入一層數組前,那么元素序列號就 +1,該循環完成並返回值后,元素序列號 - 1, 回到當前層次的數組中繼續遍歷。
注: 如果當前數組為空,數組序列號應該為當前數組層次,這是為了判斷在所有元素師空數組時的情況。如[[],[]]返回'11'、[[[],[]]]返回'22'。