• 只出现一次的数字


                                                                            只出现一次的数字


    本次题目要求为:

    给定一个非空整数数组,除了某个元素只出现一次以外,其余每个元素均出现两次。找出那个只出现了一次的元素。

    说明:

    你的算法应该具有线性时间复杂度。 你可以不使用额外空间来实现吗?

    示例 1:

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

    示例 2:

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

    在这里提供4中解决方法:

    1、使用HashSet

     1     //1.0
     2     public int singleNumber(int[] nums) {
     3         Set<Integer> set = new HashSet<>();
     4         //遍历数组,把其中的值写入set中
     5         for (int a : nums) {
     6             if (!set.add(a)) {
     7                 //若set中已有重复值,就把该值删除,这样遍历结束后的值便是唯一值
     8                 set.remove(a);
     9             }
    10         }
    11         return set.iterator().next();
    12     }

    2、先将传入的数组排序,再处理

     1     //2.0
     2     public int singleNumber(int[] nums) {
     3         Arrays.sort(nums);//对数组进行排序
     4         //因为排好序后的数组中的元素除了要寻找的那个值以外,都是成对出现的,
     5         //所以,以每次递增2的规律遍历数组
     6         for (int i = 0; i < nums.length - 1; i+=2) {
     7             //当前值与它后面的值不相等,则它就是寻找值
     8             if (nums[i] != nums[i + 1]) {
     9                 return nums[i];
    10             }
    11             
    12         }
    13         //遍历结束后,没有找到寻找值,则它位于数组末尾,
    14         //只有这一种情况下,遍历才会找不到该值
    15         return nums[nums.length - 1];
    16         
    17     }

    3、分析一下这个场景下的数组,有一个规律,即我们要寻找的值在数组中的索引总是偶数,这样我们用数组中偶数下标的和减去奇数下标的和,差值就是答案

     1     //3.0
     2     public int singleNumber(int[] nums) {
     3         int num = 0;
     4         Arrays.sort(nums);//对数组排序
     5         for (int i = 0; i < nums.length; i++) {
     6             //通过i%2这个运算来判断当前元素是奇数位还是偶数位,只有为偶数位时运算值才为0
     7             //若元素是偶数位,则num加上它的值,否则减去它的值
     8             num = (i % 2 == 0) ? num + nums[i] : num - nums[i];
     9         }
    10         return num;
    11     }

    4、回忆一下异或运算(^)的规则,参与运算的两个数的值不一致时返回1,否则返回0,另外,0与任何数(a)异或的结果都为它本身(a),利用这个特性,完成算法

     1     //4.0
     2     public int singleNumber(int[] nums) {
     3         int result = 0;
     4         for (int num : nums) {
     5             //因为0与任何数异或的结果都是它本身,不会影响结果,所以算法入口,
     6             //我们让0与第一个值异或,来开启下面的运算
     7             result = num ^ result;
     8         }
     9         return result;
    10         
    11     }

    测试方法:

     1 package onceTime;
     2 
     3 /**
     4  * 
     5  * @author Cone
     6  * @since 2019年4月21日
     7  *
     8  */
     9 public class TestSolution {
    10 
    11     public static void main(String[] args) {
    12         
    13         Solution solution = new Solution();
    14         int[] a = new int[] {
    15                 4,1,2,1,2
    16         };
    17         System.out.println(solution.singleNumber(a));
    18 
    19     }
    20 
    21 }

    总结

    以上四种方法,最后一种算法我个人是最喜欢的,它巧妙的运用了异或运算,JDK提供的排序算法确实好用,但是我更想实现自己的方法,对,自己造轮子。

  • 相关阅读:
    格式与布局
    iframe
    tp
    头信息
    php 文件下载
    socket
    Flex 布局2
    Flex 布局
    下拉刷新
    选取一种类中含有某一属性值得元素的集合
  • 原文地址:https://www.cnblogs.com/cone/p/10746162.html
Copyright © 2020-2023  润新知