zoukankan      html  css  js  c++  java
  • leetcode-数组中只出现一次的数字

    一、版本1—有序数组中只出现一次的数字

    1、题目描述

      给定一个只包含整数的有序数组,每个元素都会出现两次,唯有一个数只会出现一次,找出这个数。

      示例 1:

    输入: [1,1,2,3,3,4,4,8,8]
    输出: 2

      示例 2:

    输入: [3,3,7,7,10,11,11]
    输出: 10

      注意: 您的方案应该在 O(log n)时间复杂度和 O(1)空间复杂度中运行。

    2、思路

      a)使用线性时间异或运算:

      

      b)实现规定时间复杂度的方法

    3、代码

      a)使用异或运算实现的代码

     1 package cn.zifuchuan;
     2 
     3 public class Test7 {
     4 
     5     public static void main(String[] args) {
     6         int[] nums = {1,1,2,3,3,4,4,8,8};
     7         System.out.println(singleNonDuplicate(nums));
     8     }
     9     
    10     public static int singleNonDuplicate(int[] nums) {
    11         int temp = 0;
    12         for (int i = 0; i < nums.length; i++) {
    13             temp ^= nums[i];
    14         }
    15         return temp;
    16     }
    17 }

       b)二分法查找实现

     1 package cn.zifuchuan;
     2 
     3 public class Test7 {
     4 
     5     public static void main(String[] args) {
     6         int[] nums = {1, 1, 2, 2, 4, 4, 5, 5,9};
     7         System.out.println(singleNonDuplicate(nums));
     8     }
     9     
    10 //    public static int singleNonDuplicate(int[] nums) {
    11 //        int temp = 0;
    12 //        for (int i = 0; i < nums.length; i++) {
    13 //            temp ^= nums[i];
    14 //        }
    15 //        return temp;
    16 //    }
    17     
    18     public static int singleNonDuplicate(int[] nums) {
    19         int low = 0, high = nums.length - 1;
    20         int mid = (high - low) / 2;
    21         while(low < mid) {
    22             if((nums[mid] == nums[mid - 1])) { //和左边相等,那么出现一次的就在右边            
    23                 if((mid - low) % 2 != 0) {
    24                     low = mid + 1;
    25                     System.out.println("low=" + low + "nums[low]" + nums[low]);
    26                 } else {
    27                     high = mid - 2;
    28                     System.out.println("high=" + high + "nums[high]" + nums[high]);
    29                 }
    30             } else if(nums[mid] == nums[mid + 1]){ //和右边相等,出现一次的就在左边
    31                 if((mid - low) % 2 != 0) {
    32                     high = mid - 1;
    33                     System.out.println("high=" + high + "nums[high]" + nums[high]);
    34                 } else {
    35                     low = mid + 2;
    36                     System.out.println("low=" + low + "nums[low]" + nums[low]);
    37                 }
    38             }
    39             mid = (high - low) / 2 + low; //二分中间位置
    40             System.out.println("mid=" + mid + "mid:" + nums[mid]);
    41         }
    42 //        System.out.println(mid);
    43         return nums[low];
    44     }
    45 }

     二、版本二—无须数组中找出两个只出现一次的数字

    1、题目描述

      给定一个整数数组 nums,其中恰好有两个元素只出现一次,其余所有元素均出现两次。 找出只出现一次的那两个元素。

      示例 :

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

      注意:

    1、结果输出的顺序并不重要,对于上面的例子, [5, 3] 也是正确答案。
    2、你的算法应该具有线性时间复杂度。你能否仅使用常数空间复杂度来实现?

    2、代码实现

      a)位运算实现

    1     public int singleNumber(int[] nums) {
    2         int a = 0, b = 0;
    3         for (int i = 0; i < nums.length; i++) {
    4             a = (a ^ nums[i]) & ~b;
    5             b = (b ^ nums[i]) & ~a;
    6         }
    7         return a;
    8     }

      b)排序之后实现

     1     public static int singleNumber(int[] nums) {
     2         int len = nums.length;
     3         Arrays.sort(nums);
     4         for (int i = 0; i < len; i++) {
     5             if(((i + 1) < (len - 1)) && (nums[i] == nums[i + 1]) ) {
     6                 i = i + 2;
     7                 continue;
     8             } else if(((i+1) < (len - 1)) && (nums[i] != nums[i + 1])){
     9                 return nums[i];
    10             } else {
    11                 return nums[len-1];
    12             }
    13         }
    14         return 0;
    15     }
  • 相关阅读:
    穷举、迭代、以及while代替for循环的使用
    for循环与for循环嵌套
    day07 数据类型补充
    day06
    day05
    day04
    python2 和 python3 的区别
    day03
    第一周笔记
    day02笔记
  • 原文地址:https://www.cnblogs.com/fsmly/p/10568397.html
Copyright © 2011-2022 走看看