算法专题(哈希表MAP)

136 阅读1分钟

宝石与石头

771. 宝石与石头

 给你一个字符串 jewels 代表石头中宝石的类型,另有一个字符串 stones 代表你拥有的石头。 stones 中每个字符代表了一种你拥有的石头的类型,你想知道你拥有的石头中有多少是宝石。

字母区分大小写,因此 "a" 和 "A" 是不同类型的石头。

示例 1:

输入: jewels = "aA", stones = "aAAbbbb"
输出: 3

示例 2:

输入: jewels = "z", stones = "ZZ"
输出: 0

提示:

  • 1 <= jewels.length, stones.length <= 50
  • jewels 和 stones 仅由英文字母组成
  • jewels 中的所有字符都是 唯一的
/**

 * @param {string} jewels

 * @param {string} stones

 * @return {number}

 */

 var numJewelsInStones = function(jewels, stones) {

    const map=new Map()

    for(let stone of stones){

        map.set(stone,map.has(stone) ? map.get(stone)+1 : 1)

    }

    let count=0

    for(let j of jewels){

        count+=map.has(j) ? map.get(j) : 0

    }

    return count

};

字符流中第一个不重复字符

请实现一个函数用来找出字符流中第一个只出现一次的字符。例如,当从字符流中只读出前两个字符"go"时,第一个只出现一次的字符是"g"。 当从该字符流中读出前六个字符“google"时,第一个只出现一次的字符是"l"。
如果当前字符流没有存在出现一次的字符,返回#字符。
要求获得第一个只出现一次的。
使用一个有序的存储结构为每个字符计数,再遍历这个对象,第一个出现次数为1的即为结果。
在JavaScript中有序存储空间选择对象即可。
上述解决办法是有问题的,因为在JavaScript中对象遍历并不是在所有浏览器中的实现都是有序的,而且直接使用对象存储,当字符流中出现数字时也是有问题的。\

所以下面改用剑指offer中的解法

  • 创建一个长度为256的数组container来标记字符流中字符出现的次数

  • 使用字符ASCII码作为下标,这样数组长度最大为256

  • 当字符没有出现过,标记为-1

  • 当字符只出现一次,标记为字符在字符流中的位置index

  • 当字符出现多次时,标记为-2

  • 当调用FirstAppearingOnce时,只需要找到,数组值大于-1的且值最小的位置索引,即为第一个出现次数为1的字符

    let container = new Array(256).fill(-1);
    let index = 0;
    function Init() {
      container = new Array(256).fill(-1);
      index = 0;
    }
    function Insert(ch) {
      const code = ch.charCodeAt(0);
      if (container[code] === -1) {
        container[code] = index;
      } else if (container[code] >= 0) {
        container[code] = -2;
      }
      index++;
    }
    function FirstAppearingOnce() {
      let minIndex = 256;
      let strIndex = 0;
      for (let i = 0; i < 256; i++) {
        if (container[i] >= 0 && container[i] < minIndex) {
          minIndex = container[i];
          strIndex = i;
        }
      }
      return minIndex === 256 ? '#' : String.fromCharCode(strIndex);
    }

解法二

function getFirstChar(s){
    const set=new Set(s)
    for(let i of set){
        if(s.match(new RegExp(i,'g')).length===1){
            return i
        }
    }
    return ' '
}

169. 多数元素

给定一个大小为 n 的数组,找到其中的多数元素。多数元素是指在数组中出现次数 大于 ⌊ n/2 ⌋ 的元素。\

你可以假设数组是非空的,并且给定的数组总是存在多数元素。
示例 1:
输入:[3,2,3]
输出:3
示例 2:\

输入:[2,2,1,1,1,2,2]
输出:2
进阶: 尝试设计时间复杂度为 O(n)、空间复杂度为 O(1) 的算法解决此问题。

/**

 * @param {number[]} nums

 * @return {number}

 */

var majorityElement = function(nums) {

    const half=nums.length/2

    const map=new Map()

    for(let i=0;i<nums.length;i++){

        const item=nums[i]

        map.set(item,(map.get(item) || 0)+1)

        if(map.get(item)>half) return item

    }

    return -1

};

208. 实现 Trie (前缀树)

leetcode-cn.com/problems/im…

387. 字符串中的第一个唯一字符

leetcode-cn.com/problems/fi…

347. 前 K 个高频元素

leetcode-cn.com/problems/to…

454. 四数相加 II

leetcode-cn.com/problems/4s…

287. 寻找重复数

leetcode-cn.com/problems/fi…

剑指 Offer II 010. 和为 k 的子数组

leetcode-cn.com/problems/QT…

剑指 Offer II 031. 最近最少使用缓存

leetcode-cn.com/problems/Or…

剑指 Offer II 033. 变位词组

leetcode-cn.com/problems/Or…

剑指 Offer II 034. 外星语言是否排序

leetcode-cn.com/problems/Or…