Junwen's home
  • ES6

    • ES6 Decorator
    • ES6核心特性
    • Promise&Generator
  • js原理

    • 简单实现bind、apply和call
    • 如何遍历一个dom tree
    • 实现函数currying
    • 实现一个event
    • 详解js的继承
    • 详解requestAnimationFrame
    • Canvas api详解
    • DOM事件
    • EventLoop详解
    • JavaScript的内存管理
    • JavaScript的运行机制
    • Math对象
    • new操作符都做了什么
    • create基本实现原理
    • Set、Map、WeakSet和WeakMap
    • web worker原理
    • WebGL教程(MDN)
  • jsInfoSeries

    • 简介
    • JavaScript基础知识
    • 基础知识2
    • 基础知识3
    • 基础知识4
  • 技巧

    • 5个js解构有趣用途
    • 如何使用set提高代码性能
    • cordova构建项目时的问题
    • js中轻松遍历对象属性的几种方式
  • 怎么写出更好的css
  • BFC详解
  • box-shadow详解
  • CSS小技巧
  • Grid布局详解
HTML
  • IP十问
  • http笔试
  • http协议
  • 浏览器原理
  • 浏览器缓存其实就这么一回事儿
  • 浏览器兼容性问题
  • 移动端开发兼容性适配
  • 前端性能优化
  • 前端如何进行seo优化
  • webpack

    • webpack HMR
    • webpack优化基本方法
  • leetcode题解

    • 两数之和
    • 判断整数是否为回文串
    • 无重复字符的最长子串
  • Js链表
  • JavaScript排序
  • React

    • 虚拟DOM原理理解
    • React Hook
    • 组件复用指南
  • Vue

    • Vue举一反三
面试题
读书笔记
GitHub (opens new window)

Syun0216

多读书多种树
  • ES6

    • ES6 Decorator
    • ES6核心特性
    • Promise&Generator
  • js原理

    • 简单实现bind、apply和call
    • 如何遍历一个dom tree
    • 实现函数currying
    • 实现一个event
    • 详解js的继承
    • 详解requestAnimationFrame
    • Canvas api详解
    • DOM事件
    • EventLoop详解
    • JavaScript的内存管理
    • JavaScript的运行机制
    • Math对象
    • new操作符都做了什么
    • create基本实现原理
    • Set、Map、WeakSet和WeakMap
    • web worker原理
    • WebGL教程(MDN)
  • jsInfoSeries

    • 简介
    • JavaScript基础知识
    • 基础知识2
    • 基础知识3
    • 基础知识4
  • 技巧

    • 5个js解构有趣用途
    • 如何使用set提高代码性能
    • cordova构建项目时的问题
    • js中轻松遍历对象属性的几种方式
  • 怎么写出更好的css
  • BFC详解
  • box-shadow详解
  • CSS小技巧
  • Grid布局详解
HTML
  • IP十问
  • http笔试
  • http协议
  • 浏览器原理
  • 浏览器缓存其实就这么一回事儿
  • 浏览器兼容性问题
  • 移动端开发兼容性适配
  • 前端性能优化
  • 前端如何进行seo优化
  • webpack

    • webpack HMR
    • webpack优化基本方法
  • leetcode题解

    • 两数之和
    • 判断整数是否为回文串
    • 无重复字符的最长子串
  • Js链表
  • JavaScript排序
  • React

    • 虚拟DOM原理理解
    • React Hook
    • 组件复用指南
  • Vue

    • Vue举一反三
面试题
读书笔记
GitHub (opens new window)
  • ES6

    • ES6 Decorator
    • ES6核心特性
    • Promise&Generator
  • js原理

    • 简单实现bind、apply和call
    • 如何遍历一个dom tree
    • 实现函数currying
    • 实现一个event
    • 详解js的继承
    • 详解requestAnimationFrame
    • Canvas api详解
    • DOM事件
    • EventLoop详解
    • JavaScript的内存管理
    • JavaScript的运行机制
    • Math对象
    • new操作符都做了什么
    • Object.create基本实现原理
    • Set、Map、WeakSet和WeakMap
    • web worker原理
    • WebGL教程(MDN)
  • jsInfoSeries

    • 简介
    • JavaScript基础知识
    • 基础知识2
    • 基础知识3
    • 基础知识4
  • 技巧

    • 5个js解构有趣用途
    • 如何使用set提高代码性能
      • cordova构建项目时的问题
      • js中轻松遍历对象属性的几种方式
    • JavaScript
    junwen
    2021-03-20

    如何使用set提高代码性能

    参考https://juejin.im/post/5d2284dc51882579df4a4cee (opens new window)

    # Set 有何不同

    最根本的区别是数组是一个索引集合,这说明数组中的数据值按索引进行排序。
    set是一个键的集合。set不适用索引,而是使用键对数据排序。set中的元素按从插入顺序是可迭代的,他不能包含任何重复的数据。

    # set的好处

    • 查看元素:使用indexOf或includes检查数组中的项是否存在比较慢
    • 删除元素:根据value来删除该项
    • 保存NaN:数组不能使用indexOf或includes来查找NaN,而set可以保存此值。
    • 删除重复项:Set对象志存存唯一的值

    # 时间复杂度

    数组在搜索元素方法时间复杂度为0(N)。也就是运行时间的增长速度与数组的长度相同。
    Set用于搜索、删除和插入元素时间复杂度都只有0(1)

    # 比较Set和Array

    let arr = [], set = new Set(), n = 100000;
    for(let i=0;i<n;i++) {
      arr.push(i);
      set.add(i);
    }
    
    1
    2
    3
    4
    5
    • 查找元素
    let result;
    console.time('Array'); 
    result = arr.indexOf(123123) !== -1; 
    console.timeEnd('Array');
    console.time('Set'); 
    result = set.has(123123); 
    console.timeEnd('Set');
    
    
    1
    2
    3
    4
    5
    6
    7
    8

    Array: 0.173ms
    Set: 0.023ms

    • 添加元素
    console.time('Array'); 
    arr.push(n);
    console.timeEnd('Array');
    console.time('Set'); 
    set.add(n);
    console.timeEnd('Set');
    
    1
    2
    3
    4
    5
    6

    Array: 0.018ms
    Set: 0.003ms

    • 删除元素
    const deleteFromArr = (arr, item) => {
      let index = arr.indexOf(item);
      return index !== -1 && arr.splice(index, 1);
    }
    
    console.time('Array'); 
    deleteFromArr(arr, n);
    console.timeEnd('Array');
    console.time('Set'); 
    set.delete(n);
    console.timeEnd('Set');
    
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12

    Array: 1.122ms
    Set: 0.015ms

    # 案例1:从数组中删除重复值

    const duplicateCollection = [1,2,1,3,2,4];
    let uniqueCollection = [...new Set(duplicateCollection)]; // [1,2,3,4];
    
    1
    2

    # 案例2:谷歌面试题问题

    给定一个整数无序数组和变量 sum,如果存在数组中任意两项和使等于 sum 的值,则返回true。否则,返回false。例如,数组[3,5,1,4]和 sum = 9,函数应该返回true,因为4 + 5 = 9。

    解决这个问题的一个很好的方法是遍历数组,创建 Set保存相对差值。

    const findSum = (arr, val) => {
      let searchValues = new Set();
      searchValues.add(val - arr[0]);
      for (let i = 1, length = arr.length; i < length; i++) {
        let searchVal = val - arr[i];
        if (searchValues.has(arr[i])) {
          return true;
        } else {
          searchValues.add(searchVal);
        }
      };
      return false;
    };
    
    //简洁版
    const findSum = (arr, sum) =>
      arr.some((set => n => set.has(n) || !set.add(sum - n))(new Set));
    
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18

    因为Set.prototype.has()的时间复杂度仅为O(1),所以使用 Set 来代替数组,最终使整个解决方案的线性运行时为O(N)。 如果使用 Array.prototype.indexOf()或Array.prototype.includes(),它们的时间复杂度都为 O(N),则总运行时间将为O(N²),慢得多!

    在Github上编辑此页 (opens new window)
    #JavaScript
    上次更新: 3/22/2021, 3:14:54 AM
    5个js解构有趣用途
    cordova构建项目时的问题

    ← 5个js解构有趣用途 cordova构建项目时的问题→

    最近更新
    01
    如何打造全链路项目生命周期的统一交付平台
    04-10
    02
    如何建立前端标准化研发流程
    04-10
    03
    如何从0到1一步步成体系地搭建CI
    04-10
    更多文章>
    Theme by Vdoing | Copyright © 2019-2021 Syun
    • 跟随系统
    • 浅色模式
    • 深色模式
    • 阅读模式