zoukankan      html  css  js  c++  java
  • LeetCode 380. Insert Delete GetRandom O(1) 常数时间插入、删除和获取随机元素(C++/Java)

    题目:

    Design a data structure that supports all following operations in averageO(1) time.

    1. insert(val): Inserts an item val to the set if not already present.
    2. remove(val): Removes an item val from the set if present.
    3. getRandom: Returns a random element from current set of elements. Each element must have the same probability of being returned.

    Example:

    // Init an empty set.
    RandomizedSet randomSet = new RandomizedSet();
    
    // Inserts 1 to the set. Returns true as 1 was inserted successfully.
    randomSet.insert(1);
    
    // Returns false as 2 does not exist in the set.
    randomSet.remove(2);
    
    // Inserts 2 to the set, returns true. Set now contains [1,2].
    randomSet.insert(2);
    
    // getRandom should return either 1 or 2 randomly.
    randomSet.getRandom();
    
    // Removes 1 from the set, returns true. Set now contains [2].
    randomSet.remove(1);
    
    // 2 was already in the set, so return false.
    randomSet.insert(2);
    
    // Since 2 is the only number in the set, getRandom always return 2.
    randomSet.getRandom();

    分析:

    设计一个数据结构支持以下几个操作。

    insert(val): 当元素 val 不存在时,向集合中插入该项。
    remove(val): 元素 val 存在时,从集合中移除该项。
    getRandom: 随机返回现有集合中的一项。每个元素应该有相同的概率被返回。

    我们使用HashMap来支持插入和移除操作,利用数组来支持对数据的随机访问。插入元素时,将val和该val在数组中索引值存入map中,新插入的元素实际上在数组中的索引就是数组还有元素的个数,将元素加到动态数组的尾端。

    移除元素时,为了能够达到O(1),除了将val在map中移除,还要对数组进行操作,如果单纯的将val所对应的索引处的元素删除,由于后续的所有元素都要向前移动,这样会浪费大量的时间。我们知道数组移除最后一个元素的时间复杂度时O(1),我们将要移除的元素和数组的最后一个元素交换,也可以将最后一个元素覆盖到要移除元素的位置,同时修改最后一个元素在map中对应的索引,最后删除掉数组最后一个元素,就可以保证常数时间的移除操作。最后在数组大小的范围内产生随机数,返回对应的元素,即可实现随机访问。

    程序:

    C++

    class RandomizedSet {
    public:
        /** Initialize your data structure here. */
        RandomizedSet() {
            
        }
        
        /** Inserts a value to the set. Returns true if the set did not already contain the specified element. */
        bool insert(int val) {
            if(m.count(val))
                return false;
            m[val] = v.size();
            v.push_back(val);
            return true;
        }
        
        /** Removes a value from the set. Returns true if the set contained the specified element. */
        bool remove(int val) {
            if(!m.count(val))
                return false;
            int index = m[val];
            m[v.back()] = index;
            v[index] = v.back();
            m.erase(val);
            v.pop_back();
            return true;
        }
        
        /** Get a random element from the set. */
        int getRandom() {
            int index = rand() % v.size();
            return v[index];
        }
    private:
        unordered_map<int, int> m;
        vector<int> v;
    };

    Java

    class RandomizedSet {
    
        /** Initialize your data structure here. */
        public RandomizedSet() {
            
        }
        
        /** Inserts a value to the set. Returns true if the set did not already contain the specified element. */
        public boolean insert(int val) {
            if(map.containsKey(val))
                return false;
            map.put(val, list.size());
            list.add(val);
            return true;
        }
        
        /** Removes a value from the set. Returns true if the set contained the specified element. */
        public boolean remove(int val) {
            if(!map.containsKey(val))
                return false;
            int index = map.get(val);
            map.put(list.get(list.size()-1), index);
            list.set(index, list.get(list.size()-1));
            list.remove(list.size()-1);
            map.remove(val);
            return true;
        }
        
        /** Get a random element from the set. */
        public int getRandom() {
            Random r = new Random();
            return list.get(r.nextInt(list.size()));
        }
        private HashMap<Integer, Integer> map = new HashMap<>();
        private ArrayList<Integer> list = new ArrayList<>();
    }
  • 相关阅读:
    周末之个人杂想(十三)
    PowerTip of the DaySorting Multiple Properties
    PowerTip of the DayCreate Remoting Solutions
    PowerTip of the DayAdd Help to Your Functions
    PowerTip of the DayAcessing Function Parameters by Type
    PowerTip of the DayReplace Text in Files
    PowerTip of the DayAdding Extra Information
    PowerTip of the DayPrinting Results
    Win7下IIS 7.5配置SSAS(2008)远程访问
    PowerTip of the DayOpening Current Folder in Explorer
  • 原文地址:https://www.cnblogs.com/silentteller/p/12245330.html
Copyright © 2011-2022 走看看