努力前端【LeetCode-8】645. 错误的集合 [数组筛选]

题目描述

集合 s 包含从 1 到 n 的整数。不幸的是,因为数据错误,导致集合里面某一个数字复制了成了集合里面的另外一个数字的值,导致集合 丢失了一个数字 并且 有一个数字重复 。

给定一个数组 nums 代表了集合 S 发生错误后的结果。

请你找出重复出现的整数,再找到丢失的整数,将它们以数组的形式返回。

示例 1: 输入:nums = [1,2,2,4] 输出:[2,3]

示例 2:输入:nums = [1,1] 输出:[1,2]

来源:力扣(LeetCode)
链接:https://leetcode.cn/problems/set-mismatch
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

一、数学解法

时间复杂度O(n)+O(n) = O(2n) = O(n)
首先定义三个变量:

  • sum:nums数组所有元素的和
  • sumSet:nums数组去重后所有元素的和
  • total:1-n的和 可使用等差数列公式计算

重复的数 = sum - sumSet
缺失的数 = total - sumSet

/**
 * @param {number[]} nums
 * @return {number[]}
 */
var findErrorNums = function(nums) {
    let n = nums.length
    let sum=0,sumSet=0
    let total = (1+n)*n/2
    
    for(let i=0;i<n;i++){
        sum += nums[i]
    }
    
    const arr = [...new Set(nums)]
    for(let j=0;j<arr.length;j++){
        sumSet += arr[j]
    }

    return [sum-sumSet, total - sumSet]
};

二、扫描数组

循环数组解题:时间复杂度O(n)
首先对数据进行升序排序,重复数字为nums[i] == nums[i-1]
丢失的数字有以下三种情况:

  • 当nums[0] != 1,丢失的数字是1
  • 当nums[-1] != len(nums),丢失的数字是len(nums)
  • 那么当nums[i ] - nums[i-1] = 2时, 丢失的数字为nums[i] - 1
var findErrorNums = function(nums) {
    let n = nums.length
    let lose = 0,repeat =0 
    nums.sort((a,b)=>a-b)
    if(nums[0]!=1){
        lose = 1
    }
    if(nums[n-1]!=n){
        lose = n
    }
    for(let i=1;i<n;i++){
        if(nums[i]==nums[i-1]){
            repeat = nums[i]
        }
        if(nums[i]-nums[i-1]==2){
            lose = nums[i] -1
        }
    }
    return [repeat,lose]
};

三、哈希表map

时间复杂度和空间复杂度都为O(n)
首先使用1-n的数字建立map,键就是num,值为出现次数
然后出现2次就是重复的,0次就是缺失的

var findErrorNums = function(nums) {
    let n = nums.length
    let lose = 0,repeat =0 
    const map = new Map()
    nums.forEach(num=>{
        map.set(num, (map.get(num) || 0) + 1)
    })
    for(let i = 1; i <= n; i++){
        const count = map.get(i) || 0
        if(count == 2) repeat = i
        if(count == 0) lose = i
        
    }
    return [repeat,lose]
};
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值