生成N内不出现在给定blacklist的随机数。实际有效长度len = N -blacklist.size()。如果让len外数字替换len内出现在blacklist的数字,然后以长度len作为新长度生成随机数,问题就解决了。 因此可以用一个额外的map记录下blacklist中在len内的坑对应len外合法的数字。
/* * @lc app=leetcode id=710 lang=cpp * * [710] Random Pick with Blacklist * * https://leetcode.com/problems/random-pick-with-blacklist/description/ * * algorithms * Hard (32.01%) * Likes: 199 * Dislikes: 46 * Total Accepted: 8.2K * Total Submissions: 25.4K * Testcase Example: '["Solution", "pick", "pick", "pick"]\n[[1, []], [], [], []]' * * Given a blacklist B containing unique integers from [0, N), write a function * to return a uniform random integer from [0, N) which is NOT in B. * * Optimize it such that it minimizes the call to system’s Math.random(). * * Note: * * * 1 <= N <= 1000000000 * 0 <= B.length < min(100000, N) * [0, N) does NOT include N. See interval notation. * * * Example 1: * * * Input: * ["Solution","pick","pick","pick"] * [[1,[]],[],[],[]] * Output: [null,0,0,0] * * * Example 2: * * * Input: * ["Solution","pick","pick","pick"] * [[2,[]],[],[],[]] * Output: [null,1,1,1] * * * Example 3: * * * Input: * ["Solution","pick","pick","pick"] * [[3,[1]],[],[],[]] * Output: [null,0,0,2] * * * Example 4: * * * Input: * ["Solution","pick","pick","pick"] * [[4,[2]],[],[],[]] * Output: [null,1,3,1] * * * Explanation of Input Syntax: * * The input is two lists: the subroutines called and their arguments. * Solution's constructor has two arguments, N and the blacklist B. pick has no * arguments. Arguments are always wrapped with a list, even if there aren't * any. * */classSolution {public: unordered_map<int,int> m;int len; Solution(int N,vector<int>& blacklist) { len = N -blacklist.size(); unordered_set<int> st; // len外for (int i = len; i < N; ++i) {st.insert(i); } // 去掉blacklist中的for (constauto num : blacklist) st.erase(num);auto it =st.begin();for (constauto num : blacklist) { // 把len内blacklist中的数map到len外正常数if (num < len) m[num] =*it++; } }intpick() {int k =rand() % len;returnm.count(k) ?m[k] : k; }};/** * Your Solution object will be instantiated and called as such: * Solution* obj = new Solution(N, blacklist); * int param_1 = obj->pick(); */