1 题目描述
2 算法思路
本题常见解法如下:
- 1.哈希表统计法:遍历数组| nums , 用HashMap统计各数字的数量,最终超过数组长度一半的数字则为众数。 此方法时间和空间复杂度均为O(N)。
- 2.数组排序法:将数组nums 排序,于众数的数量超过数组长度-半, 因此数组中点的元素-定为众数。仿法时间复杂度O(Nlog2N)。
- 3.摩尔投票法:核心理念为 “正负抵消”;时间和空间复杂度分别为O(N)和O(1) ;是本题的最佳解法。
摩尔投票法: 假设众数是 x
- 投票数和:如果当前数是众数,那么投票数 vote++ ,否则 vote--,因为众数大于一半,因此所有数字一定可得,vote > 0
- 正负抵消:当 前 n 个数字的vote == 0时,那么就一定可知,后面的vote > 0
思路:
- 利用正负抵消的性质,我们可以假设第一个元素是众数,然后开始向后遍历
- 每次遍历后,如果vote ==0,那么就说明,前面的元素可以抛弃不看,后面的vote 一定 大于0
- 因此每次更新 vote ==0 后的数为众数
- 如果当前数 真的就是众数,那么一直到末尾的vote > 0
- 如果当前数不是众数,那么就一直会存在 vo== 0 的时刻,会进行众数更新
- 利用这种特性,只需要一次遍历即可完成,因此时间复杂度是线性的。
3 代码
class Solution {
public int majorityElement(int[] nums) {
int x= 0;
int vote = 0;
for(int num : nums){
if(vote == 0) //更新众数
x = num;
vote += x == num ? 1 : -1; //如果是众数,就加1,不是就减1
}
return x;
}
}
4 提交结果