摘要:因?yàn)槭褂枚鄮У慕涌诖嫒?shù)據(jù)所以不用擔(dān)心與內(nèi)置屬性重名修改上面的方法后得到除了以外還有這種數(shù)據(jù)類型這是一個(gè)集合它不允許重復(fù)元素出現(xiàn)。
NaN
NaN屬于number,也是一種基本數(shù)據(jù)類型,只要有一邊是 NaN,那么結(jié)果就是false
原始值和包裝對(duì)象包裝對(duì)象即基本數(shù)據(jù)類型經(jīng)過(guò)包裝之后得到的對(duì)象,作為基本類型值的字符串擁有trim等方法,及l(fā)ength屬性,正是由于JS代碼會(huì)對(duì)原始值做一次包裝,然后變?yōu)榱俗址畬?duì)象,再執(zhí)行相關(guān)的操作。
// "a".trim(); //該過(guò)程在JS解析過(guò)程中真實(shí)存在 var tmp = new String("a"); tmp.trim();
原始值和包裝對(duì)象的區(qū)別在于類型不同。這是最根本的區(qū)別,而且雖然是包裝"對(duì)象",但也會(huì)有對(duì)象的少部分特性,比如:
var A = new String("a"); var B = new String("a"); var C = "a"; A == B //false A == C //true對(duì)象和對(duì)象
對(duì)象可以分為三種:純對(duì)象(plain object)、實(shí)例對(duì)象、其他類型的對(duì)象。
純對(duì)象指由字面量生成,成員中不含函數(shù)和日期、正則表達(dá)式等類型的對(duì)象。純對(duì)象
一元操作符會(huì)對(duì)對(duì)象隱式轉(zhuǎn)換,對(duì)象會(huì)先調(diào)用valueOf方法,然后是toString方法,直到能轉(zhuǎn)換為基本數(shù)據(jù)類型為止。
而判斷兩個(gè)對(duì)象是不是相等時(shí),因?yàn)閷?duì)象保存在堆內(nèi)存,只有兩個(gè)對(duì)象引用同一個(gè)地址,才會(huì)相等:
{} == {}//false var a = new Object(); var b = a; console.log(a == b)
如果需要比較兩個(gè)對(duì)象的鍵名鍵值對(duì)是否相等,可以采取JSON.stringify的方法轉(zhuǎn)換后再比較。
實(shí)例對(duì)象通過(guò)構(gòu)造函數(shù)生成的對(duì)象,這樣的對(duì)象和純對(duì)象一樣無(wú)法直接進(jìn)行外部比較是否相等,可以使用構(gòu)造函數(shù)(類)提供靜態(tài)方法或?qū)嵗椒▉?lái)判斷是否相等。
其他對(duì)象指的數(shù)組、日期、正則表達(dá)式等Object衍生出來(lái)的對(duì)象,一般需要根據(jù)使用場(chǎng)景來(lái)構(gòu)造判斷方法,決定兩個(gè)對(duì)象是否相等。
例如日期對(duì)象要通過(guò)Data.prototype.getTime()方法來(lái)獲取時(shí)間戳判斷是否表示同一個(gè)時(shí)刻,正則需要toString獲取原始字面量來(lái)判斷是否是相同的正則表達(dá)式。
== 和 ===如果判斷元素是否相等的方法中,采用的是==比較運(yùn)算,兩邊的數(shù)據(jù)會(huì)發(fā)生隱式類型轉(zhuǎn)換,這就造成了影響判斷結(jié)果的因素。
在判斷Boolea、Number、String三種類型進(jìn)行不同類型的 == 比較時(shí),規(guī)則是將其轉(zhuǎn)化為數(shù)字之后再比較是否相等。
console.log( "ac" == true )//false console.log(123 == "123");//true
而undefined表示"缺少值",就是此處應(yīng)該有一個(gè)值,但是還沒(méi)有定義。它會(huì)被轉(zhuǎn)換成數(shù)字,而轉(zhuǎn)換結(jié)果為NaN,NaN不等于任何值,所以u(píng)ndefined != false;對(duì)于null來(lái)說(shuō),null表示"沒(méi)有對(duì)象",即該處不應(yīng)該有值。首先調(diào)用Object.valueOf方法返回基本類型值之后在比較,所以null != false
最后一點(diǎn)是undefined == null,這是ECMA-262標(biāo)準(zhǔn) 11.9.3 節(jié)的規(guī)定。
let arr = [12,12,9,2,0,9,8]; /* 例如:12第一次出現(xiàn)在0,之后再出現(xiàn)時(shí)index為1, 說(shuō)明第二個(gè)是重復(fù)值,所以只返回第一個(gè)12, 但是對(duì)于NaN而言indexOf只會(huì)為-1,所以不管有幾個(gè)NaN都會(huì)直接跳過(guò) */ function unique(arr){ return arr.filter(function(value,index){ return arr.indexOf(value) === index; }) } //indexOf(NaN)則一直為-1,數(shù)組中會(huì)出現(xiàn)一個(gè)或多個(gè)NaN(如果存在) function unique(arr){ let ret = []; arr.forEach(function(value){ if(ret.indexOf(value) === -1){ ret.push(value); } }) return ret; } console.log(unique(arr));
在規(guī)范中,indexOf()使用的是全等比較,只要有NaN都是無(wú)法判斷位置直接跳過(guò)的。
全等比較不能處理NaN的相等性判斷,NaN不等于任何值,包括本身。Array.prototype.includes()
Array.prototype.includes()是ES6中新增的方法,判斷數(shù)組中是否包含某個(gè)元素,上一中indexOf方法可以修改為:
function unique(arr){ let ret = []; arr.forEach(function(value){ if(!ret.includes(value)){ ret.push(value); } }) return ret; }
includes()方法內(nèi)部的比較方法是:"SameValueZero",詳細(xì)規(guī)則:
1. If Type(x) is different from Type(y), return false. 2. If Type(x) is Number,then a. If x is NaN and y is NaN, return true. b. If x is +0 and y is -0, return true. c. If x is -0 and y is +0, return true. d. If x is the same Number value as y, return true. e. Return false. 3. Return SameValueNonNumber(x, y).
注意:如果x、y都是NaN,則返回true,所以includes方法可以判斷是否包含了NaN
var arr = [12,1,"d3",NaN]; console.log(arr.includes(NaN));//true
由此可見(jiàn)indexOf和includes方法對(duì)NaN待的行為不一樣。
其他的方法遍歷是最基本也是最容易想到的方案:
function unique(arr){ let isRepeate; let ret = []; for(var i = 0;len = arr.length,i去重的部分也是全等操作符實(shí)現(xiàn)的,所以對(duì)于數(shù)組中的NaN而言也會(huì)都push進(jìn)入ret之后返回。
Map Key
Map是一種新的數(shù)據(jù)類型,就是key的類型沒(méi)有限制的對(duì)象,它的存取使用多帶帶的get、set接口。因?yàn)槭褂枚鄮У慕涌诖嫒?shù)據(jù),所以不用擔(dān)心key與內(nèi)置屬性重名,修改上面的方法后得到:
function unique(arr){ let ret = []; let len = arr.length; let tmp = new Map(); for(let i = 0;iset
除了Map以外,還有Set這種數(shù)據(jù)類型,這是一個(gè)集合,它不允許重復(fù)元素出現(xiàn)。
如果重復(fù)添加相同的元素,只會(huì)儲(chǔ)存其中的一個(gè),包括NaN在內(nèi)。如果將這種特性與數(shù)組交換,那么數(shù)組就可以直接去重了。function unique(arr){ let ret = new Set(arr); return Array.from(set); }
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://m.hztianpu.com/yun/82754.html
摘要:專題系列第三篇,講解各種數(shù)組去重方法,并且跟著寫一個(gè)前言數(shù)組去重方法老生常談,既然是常談,我也來(lái)談?wù)?。它類似于?shù)組,但是成員的值都是唯一的,沒(méi)有重復(fù)的值。 JavaScript 專題系列第三篇,講解各種數(shù)組去重方法,并且跟著 underscore 寫一個(gè) unique API 前言 數(shù)組去重方法老生常談,既然是常談,我也來(lái)談?wù)劇?雙層循環(huán) 也許我們首先想到的是使用 indexOf 來(lái)循...
摘要:數(shù)組去重,一般會(huì)在面試的時(shí)候才會(huì)碰到,要求手寫數(shù)組去重方法的代碼。在實(shí)際項(xiàng)目中碰到的數(shù)組去重,一般都是后臺(tái)去處理,很少讓前端處理數(shù)組去重。數(shù)組去重的方法一利用去重中最常用如果不考慮兼容性,這種去重的方法代碼最少。 數(shù)組去重,一般會(huì)在面試的時(shí)候才會(huì)碰到,要求手寫數(shù)組去重方法的代碼。如果是被提問(wèn)到,數(shù)組去重的方法有哪些?你能答出其中的10種,面試官很有可能對(duì)你刮目相看。 在實(shí)際項(xiàng)目中碰到的...
摘要:現(xiàn)在要求去重下面這個(gè)數(shù)組測(cè)試重復(fù)重復(fù)方法一測(cè)試重復(fù)重復(fù)去重后測(cè)試重復(fù)是新加的集合集合中的值不會(huì)重復(fù)。歡迎大家一起討論提出新的去重方法。有任何錯(cuò)誤請(qǐng)?jiān)谠u(píng)論指出。 現(xiàn)在要求去重下面這個(gè)數(shù)組 [1, 2, 3, 3, 3, 0, 1, 2, 測(cè)試, 重復(fù), 重復(fù), NaN, NaN, false, false]; 方法一:ES6 Set() let arr = [1, 2, 3, 3, 3,...
摘要:現(xiàn)在要求去重下面這個(gè)數(shù)組測(cè)試重復(fù)重復(fù)方法一測(cè)試重復(fù)重復(fù)去重后測(cè)試重復(fù)是新加的集合集合中的值不會(huì)重復(fù)。歡迎大家一起討論提出新的去重方法。有任何錯(cuò)誤請(qǐng)?jiān)谠u(píng)論指出。 現(xiàn)在要求去重下面這個(gè)數(shù)組 [1, 2, 3, 3, 3, 0, 1, 2, 測(cè)試, 重復(fù), 重復(fù), NaN, NaN, false, false]; 方法一:ES6 Set() let arr = [1, 2, 3, 3, 3,...
摘要:數(shù)組去重,一般都是在面試的時(shí)候才會(huì)碰到,一般是要求手寫數(shù)組去重方法的代碼。如果是被提問(wèn)到,數(shù)組去重的方法有哪些你能答出其中的種,面試官很有可能對(duì)你刮目相看。數(shù)組去重的方法一利用去重中最常用不考慮兼容性,這種去重的方法代碼最少。 數(shù)組去重,一般都是在面試的時(shí)候才會(huì)碰到,一般是要求手寫數(shù)組去重方法的代碼。如果是被提問(wèn)到,數(shù)組去重的方法有哪些?你能答出其中的10種,面試官很有可能對(duì)你刮目相看...
閱讀 1104·2022-06-21 15:13
閱讀 1923·2021-10-20 13:48
閱讀 1098·2021-09-22 15:47
閱讀 1425·2019-08-30 15:55
閱讀 3185·2019-08-30 15:53
閱讀 578·2019-08-29 12:33
閱讀 777·2019-08-28 18:15
閱讀 3537·2019-08-26 13:58