leetcode:169. 多数元素

题目来源

题目描述

在这里插入图片描述

题目解析

摩根投票法

候选人(major)初始化为num[0],票数count初始化为1
当遇到与major相同的数,则票数count = count + 1,否则count = count - 1;
当遇到count == 0时,更好候选人major,并将票数count重置为1

  • cpp:
class Solution {
public:
    int majorityElement(vector<int>& nums) {
        int major = nums[0];
        int count = 1;

        for (int i = 1; i < nums.size(); ++i) {
            if(count == 0){
                major = nums[i];
                count = 1;
            }else{
                if(nums[i] == major){
                    count++;
                }else{
                    count--;
                }
            }
        }

        return major;
    }
};

投票算法证明:

  • 如果候选人不是maj 则 maj,会和其他非候选人一起反对 会反对候选人,所以候选人一定会下台(maj==0时发生换届选举)
  • 如果候选人是maj , 则maj 会支持自己,其他候选人会反对,同样因为maj 票数超过一半,所以maj 一定会成功当选

排序

  • 由于众数出现的频率大于n/2,所以在排序之后众数必存在于下标[n/2]处(本题默认数组中是一定存在众数的,所以返回下标[n/2]可行)
    在这里插入图片描述
int majorityElement(vector<int>& nums) {
    sort(nums.begin(), nums.end());
    return nums[nums.size() / 2];
}

在这里插入图片描述

哈希表

使用hash映射来存储每个元素以及出现的次数。对于哈希映射中的每个键值对,键表示一个元素,值表示该元素出现的次数。

我们同样也可以在遍历数组 nums 时候使用打擂台的方法,维护最大的值,这样省去了最后对哈希映射的遍历。

class Solution {
public:
    #include <unordered_map>
    int majorityElement(vector<int>& nums) {
        std::unordered_map<int, int> counts;
        int majority = 0, count = 0;
        for(int num : nums){
            ++counts[num];
            if(counts[num] > count){
                majority = num;
                count = counts[num];
            }
        }

        return majority;
    }
};

在这里插入图片描述

随机法

在这里插入图片描述

class Solution {
    // 生成一个随机坐标
    private static int randomIndex(Random rand, int low, int high){
        return rand.nextInt(high - low) + low;
    }

    // 统计当前元素出现的次数
    public static int countElement(int[] arr, int index){
        int count = 0;
        for (int i = 0; i < arr.length; i++){
            if (arr[i] == arr[index]){
                count++;
            }
        }
        return count;
    }

    public  int majorityElement(int[] nums) {
        Random rand = new Random();

        int m = nums.length / 2;
        while (true){
            int index = randomIndex(rand, 0, nums.length);
            int count = countElement(nums, index);
            if (count > m){
                return nums[index];
            }
        }
    }
}

在这里插入图片描述
在这里插入图片描述

类似题目

题目思路
leetcode:169. 无序数组中的多数元素(超过n/2) majority-element这里已经确保了主要元素一定存在,所以最后不需要验证
面试题 17.10. 无序数组中的主要元素(超过n/2) find-majority-element-lcci没有说主要元素一定存在,所以最后需要看major是否是主要元素
leetcode:229. 无序数组中的多数元素 II(超过n/3) majority-element ii
leetcode:1287. 有序数组中出现次数超过25%的元素
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值