Set对象

一、Set对象

Set 对象允许你存储任何类型的唯一值,无论是原始值或者是对象引用。

Set对象是值的集合,你可以按照插入的顺序迭代它的元素。 Set中的元素只会出现一次,即 Set 中的元素是唯一的。

在 ECMAScript 2015规范中-0  0  +0 是完全相等的。

NaNundefined都可以被存储在Set 中, NaN之间被视为相同的值(NaN被认为是相同的,尽管 NaN !== NaN)。

Number.POSITIVE_INFINITY 和 Infinity都表示正无穷数,是相同的值。

引用值地址不能相同,原始值不能相等,这才能确保值的唯一性。

创建Set对象

1、可以接受一个数组,数组的@@iterator接口的每项值作为Set对象的每项值

let set = new Set([1,2,3,4])
set.add([3,4,5]);
console.log(set);  Set(5) {1, 2, 3, 4, Array(3)}

 2、其实可以接受任何符合格式的带有@@iterator接口的对象

接受字符串:

let set = new Set("abcd");

console.log(set);   Set(4) {"a", "b", "c", "d"}

接收Set对象:

let set = new Set("abcd");
console.log(new Set(set));   Set(4) {"a", "b", "c", "d"}

接收Map对象:

let map = new Map([
  [1,"a"],
  [2,"b"]
])
console.log(new Set(map))  Set(2) {[1, "a"], [2,"b"]}

 接收Iterator对象:

let set = new Set("abcd");
let map = new Map([
  [1,"a"],
  [2,"b"]
])
console.log(new Set(set.values()));  Set(4) {"a", "b", "c", "d"}
console.log(new Set(map.values()))   Set(2) {"a", "b"}

一、属性size

 Size属性将会返回Set对象中元素的个数。

size的值是一个整数,表示Set对象有多少条目。size的集合访问函数是undefined; 你不能改变这个属性值

    let arr = [1,2,3,4];
    let set = new Set(arr);
    set.size = 2; //无效,但不报错
    console.log(set.size);// 4

二、方法

(1)add方法

add() 方法用来向一个 Set 对象的末尾 添加一项指定的值。add方法返回该Set对象,所以可以链式调用。

注意:添加重复的值是无效的。

        let arr = [3,4];
        let mySet = new Set();
        mySet.add(1)
             .add("a")
             .add([3,4])
             .add({name:"zhu"})
             .add(arr)
             .add(NaN)
             .add(undefined)

        console.log(mySet);

(2)has方法

has() 方法返回一个布尔值来指示对应的值value是否存在Set对象中。

    let arr = [1,2,3,4,NaN];
    let set = new Set(arr);
    console.log(set.has(NaN)); //true

(3)values方法、keys方法、entries方法  都返回SetIterator对象

let arr = ["a","b","c"];
let mySet = new Set(arr);
console.log(mySet); //Set(3) {"a", "b", "c"}
console.log(mySet.keys()) //SetIterator {"a", "b", "c"}
console.log(mySet.values()) //SetIterator {"a", "b", "c"}
console.log(mySet.entries())//SetIterator {"a" => "a", "b" => "b", "c" => "c"}

values() 方法返回一个 Iterator  对象,该对象按照原Set 对象元素的插入顺序返回其所有元素。兼容性Egde12。

下面两个方法兼容性不好,Set对象判断值唯一,算不上有键,keys方法和entries方法得到的结果都与键有关,与Set本意不符。 

 

keys() 方法是value()方法的别名 (与 Map 对象相似); 它的行为与 value 方法完全一致,返回 Set 对象的元素。

 

entries() 方法返回一个新的迭代器对象 ,这个对象的元素是类似 [value, value] 形式的数组,value 是集合对象中的每个元素,迭代器对象元素的顺序即集合对象中元素插入的顺序。由于集合对象不像 Map 对象那样拥有 key,然而,为了与 Map 对象的 API 形式保持一致,故使得每一个 entry 的 key 和 value 都拥有相同的值,因而最终返回一个 [value, value] 形式的数组。

 

与Map对象相比,Set对象的keys values entries方法得到的也是iterator对象。而Set对象这些方法都在处理Set对象的value值,keys得到的value,values得到是value,entries得到的是value作为键和value作为值。

返回值:一个新的包含 [value, value] 形式的数组迭代器对象,value 是给定集合中的每个元素,迭代器 对象元素的顺序即集合对象中元素插入的顺序。

(4)forEach方法

在forEach的处理函数中value和key都是value值

        let arr = [3,4];
        let mySet = new Set();
        mySet.add(1)
             .add("a")
             .add([3,4])
             .add({name:"zhu"})
             .add(arr)
             .add(NaN)
             .add(undefined)
        console.log(mySet);
        
        mySet.forEach((value, key) => {
            console.log(value);
        })

(5)delete方法

delete() 方法可以从一个 Set 对象中删除指定的元素。成功删除返回 true,否则返回 false。

let set = new Set("abcd");
set.delete("a");
console.log(set);  Set(3) {"b", "c", "d"}

(6)clear方法

let set = new Set("abcd");
set.clear();
console.log(set);  Set(0) {}

三、Map对象和Set对象与数组之间的转换

1、Set对象和Map对象都可以转换为数组

Set对象转数组:得到是Set对象的value值组成的数组。

let arr = ["a","b","c"];
let mySet = new Set(arr);
console.log(mySet); //Set(3) {"a", "b", "c"}
console.log([...mySet]); //["a","b","c"]

1)、展开运算符,将Set对象展开后,放在【】中,我们知道Set对象的结构:

Set(3) {"a", "b", "c"}

我们可以使用展开运算符先将其展开,再用[]包裹,其实是将值放在数组中。

 

2)、也可以直接通过Array.from方法,将Set对象转换为数组。

 

Map对象转数组,也是这两种方式:得到的也是数组,该数组的每项都是一个长度为2的数组,第一项是key值,第二项是value值。

        let myMap = new Map();
        myMap.set("name", "zhuzhu")
             .set(23, 24)
             .set(false, true)
             .set(["1",2], ["js","html","css"])
             .set({}, {a:1,b:2});
        console.log([...myMap]);       [Array(2), Array(2), Array(2), Array(2), Array(2)]
        console.log(Array.from(myMap));[Array(2), Array(2), Array(2), Array(2), Array(2)]

 

2、数组转Map对象和Set对象

1)数组转Set对象,且会去重:

        let arr = ["a",1,"b",2,2];
        let mySet = new Set(arr);
        console.log(mySet);       Set(4) {"a", 1, "b", 2}

2)数组转Map对象,必须是二维数组:

        let arr = [["a",1],["b",2],["c",3]];
        let myMap = new Map(arr);
        console.log(myMap);            Map(3) {"a" => 1, "b" => 2, "c" => 3}

四、Set和Map的实例应用

1、Map对象的应用

(1)Map对象的克隆(浅克隆)

arr和myMap中的arr和cloneMap中的arr指向同一个地址。

let myMap = new Map();
let arr = [1,2,3];
myMap.set("name", "zhuzhu")
      .set(23, 24)
      .set(false, true)
      .set(arr, ["js","html","css"])
      .set({}, {a:1,b:2});

let cloneMap = new Map(myMap);
console.log(cloneMap === myMap); //false 浅克隆,不是同一个地址
arr[0] = "a";
console.log(myMap); //myMap中的arr指向的地址值被修改
console.log(cloneMap) //cloneMap中的arr指向的地址值被修改

 当arr的索引被修改时,不影响myMap和cloneMap中的arr索引地址

let myMap = new Map();
let arr = [1,2,3];
myMap.set("name", "zhuzhu")
      .set(23, 24)
      .set(false, true)
      .set(arr, ["js","html","css"])
      .set({}, {a:1,b:2});

let cloneMap = new Map(myMap);
console.log(cloneMap === myMap); //false 浅克隆,不是同一个地址
arr = ["a"];
console.log(myMap); //myMap没有被修改
console.log(cloneMap) //cloneMap没有被修改

(2)Map对象的合并

var first = new Map([[1, 'one'], [2, 'two'], [3, 'three']]);
var second = new Map([[1, 'uno'], [2, 'dos']]);
 
// 合并两个 Map 对象时,如果有重复的键值,则后面的会覆盖前面的,对应值即 uno,dos, three
var merged = new Map([...first, ...second]);
console.log(merged);        Map(3) {1 => "uno", 2 => "dos", 3 => "three"}

 2、Set对象的应用

(1)数组去重

根据Set对象的唯一性和Set对象与数组之间的转换,进行数组去重

        let arr = [1,2,3,4,3,2,1];
        let mySet = new Set(arr);
        console.log([...mySet]);   [1, 2, 3, 4]

(2)数组的并集

去重后的数组arr1,进行过滤操作,过滤每一项的时候,arr1不存在另一个arr2数组中的项组成的数组和arr2合并

        let arr1 = [1,2,3,4,3,2,1];
        let arr2 = [3,4,2,5,8,9];
        let set1 = new Set(arr1);
        let set2 = new Set(arr2);

        let mergeArr = ([...set1].filter(item => !set2.has(item))).concat([...set2]);
        console.log(mergeArr);     [1, 3, 4, 2, 5, 8, 9]

(3)数组的交集

去重后的arr1和arr2,arr1进行过滤,arr2中也有项组成的数组就是交集

        let arr1 = [1,2,3,4,3,2,1];
        let arr2 = [3,4,2,5,8,9];
        let set1 = new Set(arr1);
        let set2 = new Set(arr2);

        let mergeArr = [...set1].filter(item => set2.has(item));
        console.log(mergeArr)        [2, 3, 4]

(4)数组的差集

去重后的arr1和arr2,arr1进行过滤,arr2中没有的项组成的数组和arr2进行过滤,arr1中没有的项组成的数组进行合并

let arr1 = [1,2,3,4,3,2,1];
let arr2 = [3,4,2,5,8,9];
let set1 = new Set(arr1);
let set2 = new Set(arr2);

let mergeArr = ([...set1].filter(item => !set2.has(item))).concat([...set2].filter(item => !set1.has(item)))
console.log(mergeArr);  [1, 5, 8, 9]

 

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值