• 数组中重复的数字


    找出数组中重复的数字。


    在一个长度为 n 的数组 nums 里的所有数字都在 0~n-1 的范围内(题设要点)。数组中某些数字是重复的,但不知道有几个数字重复了,也不知道每个数字重复了几次。请找出数组中任意一个重复的数字。

    示例 1:

    输入:
    [2, 3, 1, 0, 2, 5, 3]
    输出:2 或 3

    限制:

    2 <= n <= 100000


    方法一:哈希表(最自然,但是要额外空间)
    最容易想到用哈希表判重,这种方法是最自然的。

    分析:这种方法不修改原始数组,但是使用了 O(N) 空间,使用空间换时间,是最正常的思路,时间复杂度是O(N)。

    方法二:排序(也比较容易想到,但是要排序,复杂度高)
    排序以后,再遍历一遍就知道哪个重复了。

    分析:这个方法其实比较容易想到,但是时间复杂度是 O(N log N),同时也修改了原始数组。

    方法三:把数组视为哈希表(因为条件的缘故可以直接根据索引确定,这个方法重点理解)

    程序实例:

     1 import java.util.*;
     2 
     3 public class Problem03 {
     4     public static void main(String[] args) {
     5 
     6         //方法4重点理解
     7         int []nums=new int[]{2, 3, 1, 0, 2, 5, 3};
     8 
     9         System.out.println(solution3(nums));
    10     }
    11     public static int solution(int []nums){
    12         ////使用map,时间复杂度O(n),空间复杂度O(n),不改变原数组
    13         Map<Integer,Integer> map=new HashMap<>();
    14         for (int num : nums) {
    15             if(!map.containsKey(num))
    16                 map.put(num,1);
    17             else
    18                 return num;
    19         }
    20         return -1;
    21     }
    22     public static int solution2(int []nums){
    23         ////使用set,时间复杂度O(n),空间复杂度O(n),不改变原数组
    24         Set<Integer> set=new HashSet<>();
    25         for (int num : nums) {
    26             if(!set.contains(num))
    27                 set.add(num);
    28             else
    29                 return num;
    30         }
    31         return -1;
    32     }
    33     public static int solution3(int []nums){
    34         //使用排序加循环,时间复杂度O(nlogn),空间复杂度O(1)
    35         Arrays.sort(nums);
    36         int first=nums[0];
    37         for (int i = 1; i < nums.length; i++) {
    38             if(first==nums[i])
    39                 return nums[i];
    40             first=nums[i];
    41         }
    42         return -1;
    43     }
    44     public static int solution4(int []nums){
    45         //使用原地哈希(找到重复的数字就是发生了哈希冲突),时间复杂度O(n),空间复杂度O(1)
    46 
    47         //如果没有重复数字,那么正常排序后,
    48         // 数字i应该在下标为i的位置,
    49         // 所以思路是重头扫描数组,遇到下标为i的数字如果不是i的话,
    50         // (假设为m),那么我们就拿与下标m的数字交换。
    51         // 在交换过程中,如果有重复的数字发生,那么终止返回ture
    52 
    53         //{2, 3, 1, 0, 2, 5, 3},举例一步一步的走一遍
    54         int temp;
    55         for(int i=0;i<nums.length;i++){
    56             while (nums[i]!=i){
    57                 if(nums[i]==nums[nums[i]]){
    58                     //如果冲突
    59                     return nums[i];
    60                 }
    61                 temp=nums[i];
    62                 nums[i]=nums[temp];
    63                 nums[temp]=temp;
    64             }
    65         }
    66         return -1;
    67     }
    68     public static int solution5(int []nums){
    69         //使用桶排序的思想(本质是hash),时间复杂度O(n),空间复杂度O(n)
    70         //题目给了数组值的范围(小于数组长度),所以不会越界!
    71         int[] arr = new int[nums.length];
    72         for(int i = 0; i < nums.length; i++){
    73             arr[nums[i]]++;
    74             if(arr[nums[i]] > 1) return nums[i];
    75         }
    76         return -1;
    77     }
    78     
    79 
    80 }

     来源:力扣(LeetCode)
    链接:https://leetcode-cn.com/problems/shu-zu-zhong-zhong-fu-de-shu-zi-lcof



  • 相关阅读:
    HTTP状态码1XX深入理解
    小公司比较吃亏的两道微服务面试题
    趣谈IO多路复用的本质
    白话TCP/IP原理
    Windows 是最安全的操作系统
    白话linux操作系统原理
    google orgchart
    CSharp: itext7.* create pdf file
    javascript: iframe switchSysBar 左欄打開關閉,兼容各瀏覽器操作(edit)
    csharp: Cyotek.GhostScript.Pdf Conversion pdf convert image x64
  • 原文地址:https://www.cnblogs.com/treasury/p/12594214.html
Copyright © 2020-2023  润新知