阅读 100

前端算法必刷题系列[67]

这是我参与更文挑战的第 19 天,活动详情查看 更文挑战

这个系列没啥花头,就是纯 leetcode 题目拆解分析,不求用骚气的一行或者小众取巧解法,而是用清晰的代码和足够简单的思路帮你理清题意。让你在面试中再也不怕算法笔试。

128. 存在重复元素 (contains-duplicate)

标签

  • Array
  • 简单

题目

leetcode 传送门

这里不贴题了,leetcode打开就行,题目大意:

给定一个整数数组,判断是否存在重复元素

如果存在一值在数组中出现至少两次,函数返回 true 。如果数组中每个元素都不相同,则返回 false 。

示例 1:

输入: [1,2,3,1]
输出: true
复制代码

示例 2:

输入: [1,2,3,4]
输出: false
复制代码

示例 3:

输入: [1,1,1,3,3,4,3,2,4,2]
输出: true
复制代码

基本思路

排序实现

  1. 先排序,让数组的重复元素一定出现在相邻位置中
  2. 遍历判断相邻元素是否相等,有重复直接返回 true,否则返回 false

哈希表

  1. 每个元素存到哈希表中。
  2. 插入一个元素时发现该元素已经存在于哈希表中,则说明存在重复的元素。

缺点是需要额外空间。

写法实现

  1. 排序实现
var containsDuplicate = function(nums) {
    // 先排序
    nums.sort((a, b) => a - b);

    // 遍历比较相邻元素,有重复直接返回 true,否则返回 false
    for (let i = 0; i < nums.length - 1; i++) {
        if (nums[i] === nums[i + 1]) {
            return true;
        }
    }
    return false;
};

let nums = [1,2,3,1]
console.log(containsDuplicate(nums))
复制代码
  1. hashMap 实现
var containsDuplicate = function(nums) {
    let map = new Map()
    for (let i = 0; i < nums.length; i++) {
        // 当元素在hashMap中存在时,说明有重复元素
        if (map.has(nums[i])) {
            return true
        } else {
            map.set(nums[i])
        }
    }
    return false
};

let nums = [1,2,3,1]
console.log(containsDuplicate(nums))
复制代码

129. 数组中的第K个最大元素 (kth-largest-element-in-an-array)

标签

  • Array
  • 中等

题目

leetcode 传送门

这里不贴题了,leetcode打开就行,题目大意:

未排序的数组中找到第 k 个最大的元素。请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素。

说明: 你可以假设 k 总是有效的,且 1 ≤ k ≤ 数组的长度。

示例 1:

输入: [3,2,1,5,6,4] 和 k = 2
输出: 5
复制代码

示例 2:

输入: [3,2,3,1,2,4,5,5,6] 和 k = 4
输出: 4
复制代码

基本思路

快速排序

如果对快速排序不熟悉,请先看看这里的简单介绍 快速排序

我们要求第 k 个最大元素,即是从小到大排序后 第 k 个最大的元素,那么结合数组我们看:

  • 数组中的第 1 大元素,即是从小到大排序后 len - 1 下标(也就是最后一个)的元素
  • 数组中的第 k 大元素,即是从小到大排序后 len - k 下标位置的元素
  • 我们需要位置 len - k左边是比它小右边是比它大,那么 nums[len - k] 就是第 k 大的元素,这不正是快排的思想吗。(把 len-k 看作基准)

写法实现

快速排序

var findKthLargest = function (nums, k) {
  const n = nums.length;

  const quickSort = (left, right) => {
    if (left < right) {
      let pivot = nums[right];
      let pivotIndex = left;

      for (let i = left; i < right; i++) {
        if (nums[i] < pivot) {
          [nums[i], nums[pivotIndex]] = [nums[pivotIndex], nums[i]]
          pivotIndex++;
        }
      }
      [nums[right], nums[pivotIndex]] = [nums[pivotIndex], nums[right]]

      // 当 n - k == pivotIndex时
      // 左边元素比 nums[n-k] 小,右边比 nums[n-k] 大,nums[n-k] 就是第k大的元素
      if (n - k < pivotIndex) {
        // n - k 小于 pivotIndex,则在 `左边` 继续找
        quickSort(left, pivotIndex - 1);
      } else {
        // n - k 大于 pivotIndex,则在 `右边` 继续找
        quickSort(pivotIndex + 1, right);
      }
    }
  };

  quickSort(0, n - 1);
  return nums[n - k];
};


let nums = [3, 2, 3, 1, 2, 4, 5, 5, 6], k = 4
console.log(findKthLargest(nums, k))
复制代码

sort 库函数实现

var findKthLargest = function(nums, k) {
    nums.sort((a, b) => a - b)
    return nums[nums.length - k]
};

let nums = [3,2,3,1,2,4,5,5,6], k = 4
console.log(findKthLargest(nums, k))
复制代码

另外向大家着重推荐下这个系列的文章,非常深入浅出,对前端进阶的同学非常有作用,墙裂推荐!!!核心概念和算法拆解系列

今天就到这儿,想跟我一起刷题的小伙伴可以加我微信哦 点击此处交个朋友 Or 搜索我的微信号infinity_9368,可以聊天说地 加我暗号 "天王盖地虎" 下一句的英文,验证消息请发给我 presious tower shock the rever monster,我看到就通过,加了之后我会尽我所能帮你,但是注意提问方式,建议先看这篇文章:提问的智慧

参考

文章分类
前端
文章标签