原题链接在这里:https://leetcode.com/problems/random-pick-index/
题目:
Given an array of integers with possible duplicates, randomly output the index of a given target number. You can assume that the given target number must exist in the array.
Note:
The array size can be very large. Solution that uses too much extra space will not pass the judge.
Example:
int[] nums = new int[] {1,2,3,3,3}; Solution solution = new Solution(nums); // pick(3) should return either index 2, 3, or 4 randomly. Each index should have equal probability of returning. solution.pick(3); // pick(1) should return 0. Since in the array only nums[0] is equal to 1. solution.pick(1);
题解:
The question asks no more space, thus try to get pick upon original nums array.
Use Reservoir Sampling: https://www.youtube.com/watch?v=A1iwzSew5QY
Basically, when iterating nums and encounter num == target, accumlate the count and get the random between [0, count).
If random == 0, then update the res index to current index.
Time Complexity: pick, O(n).
Space: O(1). No more array space, since it is pointing to given nums.
AC Java:
1 class Solution { 2 int [] nums; 3 Random rand; 4 5 public Solution(int[] nums) { 6 this.nums = nums; 7 rand = new Random(); 8 } 9 10 public int pick(int target) { 11 int res = -1; 12 int count = 0; 13 for(int i = 0; i<nums.length; i++){ 14 if(nums[i] != target){ 15 continue; 16 } 17 18 if(rand.nextInt(++count) == 0){ 19 res = i; 20 } 21 } 22 23 return res; 24 } 25 } 26 27 /** 28 * Your Solution object will be instantiated and called as such: 29 * Solution obj = new Solution(nums); 30 * int param_1 = obj.pick(target); 31 */