• 【剑指Offer】39.数组中出现次数超过一半的数字


    题目

    给一个长度为 n 的数组,数组中有一个数字出现的次数超过数组长度的一半,请找出这个数字。

    例如输入一个长度为9的数组[1,2,3,2,2,2,5,4,2]。由于数字2在数组中出现了5次,超过数组长度的一半,因此输出2。

    数据范围:0≤n≤50000,数组中元素的值0≤val≤10000

    要求:空间复杂度O(1),时间复杂度O(n)

    输入描述:

    保证数组输入非空,且保证有解

    示例1

    输入:[1,2,3,2,2,2,5,4,2]

    返回值:2

    示例2

    输入:[3,3,3,3,2,2,2]

    返回值:3

    示例3

    输入:[1]

    返回值:1

    解答

    源代码

    1. import java.util.*;
    2. public class Solution {
    3. /**
    4. * 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
    5. *
    6. *
    7. * @param numbers int整型一维数组
    8. * @return int整型
    9. */
    10. public int MoreThanHalfNum_Solution (int[] numbers) {
    11. // write code here
    12. int cand = -1, cnt = 0;
    13. for (int num : numbers) {
    14. if (cnt == 0) {
    15. cand = num;
    16. cnt++;
    17. } else {
    18. if (cand == num) {
    19. cnt++;
    20. } else {
    21. cnt--;
    22. }
    23. }
    24. }
    25. cnt = 0;
    26. for (int num : numbers) {
    27. if (num == cand) {
    28. cnt++;
    29. }
    30. }
    31. if (cnt > numbers.length / 2) {
    32. return cand;
    33. }
    34. return 0;
    35. }
    36. }

    总结

    比较直接可以想到的方法就是用遍历数组用哈希表来存储每个数的出现次数,之后再遍历哈希表,查询是否存在一个数字出现的次数超过数组长度的一半。

    如果不想使用额外的空间,也可以对数组进行排序,如果存在这样的数字,那么它一定存在于数组中间。

    从官方题解里学习了一个很有趣的方法,如果存在一个数字出现的次数超过数组长度的一半,那么将这个数组中不相等的数字两两相消,最后剩下的一定是这个数字。

    我们用这个思路来解决问题:

    1. 初始化:候选人cand = -1, 候选人的投票次数cnt = 0

    2. 遍历数组,如果cnt=0, 表示没有候选人,则选取当前数为候选人,++cnt

    3. 否则,如果cnt > 0, 表示有候选人,如果当前数=cond,则++cnt,否则--cnt

    4. 直到数组遍历完毕,最后检查cand是否为众数

  • 相关阅读:
    Innovus GUI——不显示inst name
    全球顶尖开源项目相聚外滩大会,绘制国际化开源生态新蓝图
    100天精通Python(可视化篇)——第108天:Pyecharts绘制多种炫酷词云图参数说明+代码实战
    docker 安装 elasticsearch
    Python机器学习-多元分类的5种模型
    B树的定义和特点
    Spring Boot单元测试
    Java自动化驱动浏览器搜索稻香
    linux ssh 禁止指定用户通过ssh登录
    MybatisPlus拓展——实现多数据源操作
  • 原文地址:https://blog.csdn.net/qq_57438473/article/details/134050789