如何消除一個數(shù)組里面重復的元素?

在日常開發(fā)中,我們可能會遇到去重問題,這篇文章就是為了解決這個問題而寫的。

為了方便使用,我們可以直接把封裝的去重函數(shù)直接加入到數(shù)組的prototype中。

方法一:

Array.prototype.clearRepeat = function()?{

var arr =?[];?//定義一個臨時數(shù)組

for(var i = 0; i < this.length; i++)?{

//通過遍歷判斷當前數(shù)組下標為i的元素是否保存到臨時數(shù)組中

//如果保存,則跳過,否則保存到臨時數(shù)組

if(arr.indexOf(this[i])?==?-1)?{

arr.push(this[i]);

}

}

return arr;

};

var test =?[1, 6, 8, 8, 9, 9, 9,?"a",?"a"];

test.clearRepeat();????//結果為[1, 6, 8, 9,?"a"]

方法二:

Array.prototype.clearRepeat = function()?{

var arr =?[this[0]];?//直接定義結果數(shù)組

for(var i = 1; i < this.length; i++)?{?//從第二項開始遍歷當前數(shù)組

//對元素進行判斷:

//如果當前數(shù)組元素在此數(shù)組中第一次出現(xiàn)的位置不是i

//則第i項是重復的,否則直接存入結果數(shù)組

if(this.indexOf(this[i])?== i)?{

arr.push(this[i]);

}

}

return arr;

};

var test =?[1, 6, 8, 8, 9, 9, 9,?"a",?"a"];

test.clearRepeat();????//結果為[1, 6, 8, 9,?"a"]

上面兩種方法不推薦使用,因為indexOf()這個函數(shù)在執(zhí)行的時候每次都會遍歷一次數(shù)組,對性能影響比較大。比較適合小數(shù)據(jù)量的數(shù)組。

方法三:

Array.prototype.clearRepeat = function()?{

var h =?{};?//定義一個hash表

var arr =?[];?//定義一個臨時數(shù)組

for(var i = 0; i < this.length; i++)?{

//對元素進行判斷是否存在表中,如存在則跳過,否則存入臨時數(shù)組

if(!h[this[i]])?{

h[this[i]]?= true;?//存入hash表

arr.push(this[i]);

}

}

return arr;

};

var test =?[1, 6, 8, 8, 9, 9, 9,?"a",?"a"];

test.clearRepeat();????//結果為[1, 6, 8, 9,?"a"]

上面這種方法使用的是hash表,把已經(jīng)出現(xiàn)過的元素通過下標形式寫入一個Object中,下標的引用要比數(shù)組的indexOf()方法搜索節(jié)省時間。

順便補充下hash表的知識:

哈希表也叫散列表,是根據(jù)關鍵碼值(key, value)而進行訪問的數(shù)據(jù)結構。它通過把關鍵碼值映射到表中一個位置來訪問記錄,以加快查找速度。這個映射函數(shù)叫做散列函數(shù),存放記錄的數(shù)組叫做散列表。

關于hash表的詳細知識請點擊這里

通過測試發(fā)現(xiàn)上面這種方法存在一種缺陷,那就是當數(shù)組中同時出現(xiàn)類似于1和“1”這樣的元素時,會把“1”這樣的元素被去重。

var test?=?[1,?6,?8,?8,?9,?9,?9,?"a",?"a",?"1"];

test.clearRepeat();????//結果為[1, 6, 8, 9,?"a"],正確的應該為[1, 6, 8, 9,?"a","1"]

查閱資料發(fā)現(xiàn)原因是因為:

作為下標在轉換后會變成字符串,那么對于1和“1”這樣不同類型的值會對應到同一個下標而被去重。

修改后的代碼:

Array.prototype.clearRepeat = function()?{

var h =?{};?//定義一個hash表

var arr =?[];?//定義一個臨時數(shù)組

for(var i = 0; i < this.length; i++)?{

//對元素進行判斷是否存在表中,如存在則跳過,否則存入臨時數(shù)組

var type = typeof this[i];

if(!h[this[i]?+ type])?{

h[this[i]?+ type]?= true;

arr.push(this[i]);

}

}

return arr;

};

var test =?[1, 6, 8, 8, 9, 9, 9,?"a",?"a",?"1"];

test.clearRepeat();????//結果為[1, 6, 8, 9,?"a",?"1"]

方法四:

Array.prototype.clearRepeat = function()?{

this.sort();?//數(shù)組排序

var arr =?[this[0]];?//定義結果數(shù)組

for(var i = 1; i < this.length; i++)?{?//從第二項開始遍歷當前數(shù)組

//判斷兩個相鄰元素是否相等,如果相等說明數(shù)據(jù)重復,否則將元素寫入結果數(shù)組

if(this[i]?!== arr[arr.length - 1])?{

arr.push(this[i]);

}

}

return arr;

};

var test =?[1, 6, 8, 8, 9, 9, 9,?"a",?"a"];

test.clearRepeat();????//結果為[1, 6, 8, 9,?"a"]

上面這種方法先將數(shù)組排序,然后比較相鄰兩個元素是否相等,若相等說明重復。數(shù)組排序采用的原生sort()。

關于數(shù)組排序方法請點擊這里

上面四種方法的優(yōu)劣和性能讀者可以自行去測試。

如果你在本文中發(fā)現(xiàn)錯誤或者有異議的地方,可以在評論區(qū)留言,謝謝!

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

友情鏈接更多精彩內容