zoukankan      html  css  js  c++  java
  • leetcode 剑指 Offer 56

    leetcode 剑指 Offer 56 - II. 数组中数字出现的次数 II

    在一个数组 nums 中除一个数字只出现一次之外,其他数字都出现了三次。请找出那个只出现一次的数字。

    示例 1:

    输入:nums = [3,4,3,3]
    输出:4

    示例 2:

    输入:nums = [9,1,7,9,7,9,7]
    输出:1

    限制:

    1 <= nums.length <= 10000
    1 <= nums[i] < 2^31

    解法一:

    使用HashMap统计每个元素出现的次数,最后再遍历一次map即可

     1 class Solution {
     2     public int singleNumber(int[] nums) {
     3         
     4         // 使用HashMap的方式,使用map统计每个元素出现的次数
     5         HashMap<Integer, Integer> map = new HashMap<>();
     6         int len = nums.length;
     7         for(int i = 0; i < len; ++i){
     8             if(map.containsKey(nums[i])){
     9                 map.put(nums[i], map.get(nums[i]) + 1);
    10             }else{
    11                 map.put(nums[i], 1);
    12             }
    13         }
    14         // 遍历一遍map, 找到次数为1的数字
    15         for(Map.Entry<Integer, Integer> en: map.entrySet()){
    16             if(en.getValue() == 1){
    17                 return en.getKey();
    18             }
    19         }
    20         return 0;
    21     }
    22 }

    leetcode运行时间:17ms, 空间:39.9MB

    复杂度分析:

    空间复杂度:Map中的键值对个数, O(n/3)

    时间复杂度:一次遍历数组,一次遍历map, 所以时间复杂度为O(n)

    解法二:

     使用位运算,一个长度为32的int数组,记录了所有元素二进制在第i位的值之和,最后将数组第i位的值对3取余后将数组转换成二进制数,这个二进制数表示的数字即为该整数

     1 class Solution {
     2     public int singleNumber(int[] nums) {
     3         
     4         int[] arr = new int[32];
     5         int len = nums.length;
     6         for(int i = 0; i < len; i++){
     7             for(int j = 0; j < 32; j++){
     8                 arr[j] += (nums[i] & 1);      // 记录每个元素各个位的值
     9                 nums[i] >>= 1;
    10             }
    11         }
    12 
    13         int temp = 0;
    14         for(int i = 31; i >= 0; i--){
    15             temp <<= 1;
    16             temp |= (arr[i] % 3);         // 将temp的最后一位设置成arr[i] % 3
    17         }
    18         return temp;
    19     }
    20 }

    leetcode运行时间为:8ms, 空间为39.8mb

    复杂度分析:

    时间复杂度:时间复杂度主要是前阶段的双重 for 循环,所以时间复杂度为O(32n)

    空间复杂度:一个长度为32的 int 数组, 所以空间其实可以说是O(1), 因为空间大小是固定的,不随着nums数组的元素增多而变化。

  • 相关阅读:
    Using Resource File on DotNet
    C++/CLI VS CSharp
    JIT VS NGen
    [Tip: disable vc intellisense]VS2008 VC Intelisense issue
    UVa 10891 Game of Sum(经典博弈区间DP)
    UVa 10723 Cyborg Genes(LCS变种)
    UVa 607 Scheduling Lectures(简单DP)
    UVa 10401 Injured Queen Problem(简单DP)
    UVa 10313 Pay the Price(类似数字分解DP)
    UVa 10635 Prince and Princess(LCS N*logN)
  • 原文地址:https://www.cnblogs.com/hi3254014978/p/13735911.html
Copyright © 2011-2022 走看看