題目鏈接:
題目描述:
給定一個大小爲 n 的數組,找到其中的多數元素。多數元素是指在數組中出現次數大於 ⌊ n/2 ⌋
的元素。
你可以假設數組是非空的,並且給定的數組總是存在多數元素。
示例:
示例 1:
輸出:[3,2,3] 輸出:3
示例 2:
輸入:[2,2,1,1,1,2,2] 輸出:2
思路:
方法一:排序
如果數組中有一個數字出現的次數大於 n / 2
,那麼將數組排序之後,位於數組中間的數字一定就是那個出現次數超過一半的數字。
class Solution {
public int majorityElement(int[] nums) {
Arrays.sort(nums);
return nums[nums.length/2];
}
}
方法二:棧
數組中一個數字出現的次數大於一半,也就是說,它出現的次數比其他所有數字出現的次數和還要多。那麼我們可以用棧來記錄。分 3 種情況:
- 棧爲空,入棧;
- 棧頂元素等於當前元素,入棧;
- 否則,出棧。
最後棧頂元素即是所求。
class Solution {
public int majorityElement(int[] nums) {
Stack<Integer> stack = new Stack<>();
for (int i = 0; i < nums.length; i++) {
if (stack.empty()) {
stack.push(nums[i]);
} else if (stack.peek() == nums[i]) {
stack.push(nums[i]);
} else {
stack.pop();
}
}
return stack.peek();
}
}
方法三:方法二的優化
方法二中用棧的目的就是爲了記錄,其實並不需要真的構造一個棧,只需要一個“虛擬”的棧就可以達到目的。
可以設置一個變量 cand
表示當前棧中的元素,用另一個變量 count
表示當前棧中元素的個數,其實就是 cand
的個數。3 種情況同上:
- 棧空,入棧。修改
cand
,count++
; - 棧頂元素等於當前元素,入棧。不用修改
cand
,count++
; - 否則,出棧。
count--
。
最後 cand
即是所求。
class Solution {
public int majorityElement(int[] nums) {
int cand = nums[0], conut = 0;
for (int i = 0; i < nums.length; i++) {
if (conut == 0) {
cand = nums[i];
conut ++;
} else if (cand == nums[i]) {
conut ++;
} else {
conut --;
}
}
return cand;
}
}