有序数组中的单一元素

题目链接:https://leetcode-cn.com/problems/single-element-in-a-sorted-array/

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

示例 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)空间复杂度中运行。

解题思路:题目中已经说了使用O(log n)的时间复杂度,因此直接对数组进行排序然后再遍历的做法肯定是不可以的,因此最好用二分法来进行求解。在使用二分法进行求解就要关注该数组中位于中间的元素值的特点,以此来判断我们的答案是在中间,左边还是右边。

算法步骤:

(1)首先令low 和 high 分别指向数组首尾的两个元素,然后进行二分查找将搜索空间减半,直到找到单一元素或者仅剩一个元素为止。

(2)在进行中间元素判断时可发现如果 mid 为奇数且前半部分无单一元素的时有array[mid] = array[mid-1]  (数组从0开始计数),因此不满足这种情况就表明单一元素在前半部分,可以令 high = mid -1; 否则表明单一元素在后半部分,   可以令 low= mid + 1;

(3)当 mid 为偶数且前半部分无单一元素时有array[mid] = array[mid + 1] , 因此不满足这种情况就表明单一元素在前半部分,可以令high = mid - 2 (此时 array[mid] = array[mid - 1]); 否则表明单一元素在后半部分,可以令 low = mid + 2;

 

class Solution {
    public int singleNonDuplicate(int[] nums) {
        if (nums.length < 0) return -1;

        int low = 0;
        int high = nums.length - 1;
        
        while (low < high){
            int mid = low + (high - low) / 2;

            if (mid % 2 == 0){
                if (nums[mid] == nums[mid - 1]){
                    high = mid - 2;
                } else if (nums[mid] == nums[mid+1]){
                    low = mid + 2;
                } else {
                    return nums[mid];
                }
            }else{
                if (nums[mid] == nums[mid - 1]){
                    low = mid + 1;
                } else if (nums[mid] == nums[mid + 1]){
                    high = mid - 1;
                } else {
                    return nums[mid];
                }
            }
        }
        return nums[low];
    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值