380. O(1) 时间插入、删除和获取随机元素

参考380. O(1) 时间插入、删除和获取随机元素

题目

实现RandomizedSet 类:

  • RandomizedSet() 初始化 RandomizedSet 对象
  • bool insert(int val) 当元素 val 不存在时,向集合中插入该项,并返回 true ;否则,返回 false
  • bool remove(int val) 当元素 val 存在时,从集合中移除该项,并返回 true ;否则,返回 false
  • int getRandom() 随机返回现有集合中的一项(测试用例保证调用此方法时集合中至少存在一个元素)。每个元素应该有 相同的概率 被返回。
    你必须实现类的所有函数,并满足每个函数的 平均 时间复杂度为 O(1)

解题思路

  • 双哈希表O(1) 时间插入删除只有哈希表能实现了,用两个哈希表互相存储下标和值。
  • 数组或队列+哈希表:除了哈希表,可以用数组或队列来实现随机元素获取O(1)

双哈希表

class RandomizedSet {
    //考虑双哈希表
    HashMap<Integer,Integer> map,map2;
    Random random;
    int len = 0;
    public RandomizedSet() {
        map = new HashMap<>();
        map2 = new HashMap<>();
        random = new Random();
    }
    
    public boolean insert(int val) {
        if(map.containsKey(val)) return false;
        map.put(val,len);//下标和值互相存储
        map2.put(len++,val);
        return true;
    }
    
    public boolean remove(int val) {
        if(map.containsKey(val)) {
            int last = map2.get(len-- -1);
            if(last != val) {
                int index = map.get(val);
                map2.put(index,last);
                map.put(last,index);
            }
            map.remove(val);
            return true;
        }
        return false;
    }
    
    public int getRandom() {
        return map2.get(random.nextInt(len));
    }
}

数组+哈希表

class RandomizedSet {
    //考虑数组+哈希表
    int[] res;
    HashMap<Integer,Integer> map;
    int len = 0;
    Random random;
    public RandomizedSet() {
        res = new int[200000];
        map = new HashMap<>();
        random = new Random();
    }
    
    public boolean insert(int val) {
        if(map.containsKey(val)) return false;
        res[len] = val;
        map.put(val,len++);
        return true;
    }
    
    public boolean remove(int val) {
        if(map.containsKey(val)) {
            //用最后一个元素代替要移除的元素
            int last = res[len-1];
            int index = map.get(val);
            if(val != last) {
                res[index] = last;
                map.put(last,index);
            }
            res[len-- - 1] = 0;
            map.remove(val);
            return true;
        }
        return false;
    }
    
    public int getRandom() {
        return res[random.nextInt(len)];
    }
}

队列+哈希表

class RandomizedSet {
    //考虑队列+哈希表
    ArrayList<Integer> res;
    HashMap<Integer,Integer> map;
    Random random;
    public RandomizedSet() {
        res = new ArrayList<>();
        map = new HashMap<>();
        random = new Random();
    }
    
    public boolean insert(int val) {
        if(map.containsKey(val)) return false;
        map.put(val,res.size());
        res.add(val);
        return true;
    }
    
    public boolean remove(int val) {
        if(map.containsKey(val)) {
            //用最后一个元素代替要移除的元素
            int last = res.get(res.size()-1);
            if(val != last) {
                int index = map.get(val);
                res.set(index,last);
                map.put(last,index);
            }
            res.remove(res.size()-1);
            map.remove(val);
            return true;
        }
        return false;
    }
    
    public int getRandom() {
        return res.get(random.nextInt(res.size()));
    }
}

2023.04.27

©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容