题目:

给定一个包含 n + 1 个整数的数组 nums ,其数字都在 [1, n] 范围内(包括 1 和 n),可知至少存在一个重复的整数。

假设 nums 只有 一个重复的整数 ,返回 这个重复的数 。

你设计的解决方案必须 不修改 数组 nums 且只用常量级 O(1) 的额外空间。

示例 1:

输入:nums = [1,3,4,2,2]
输出:2
示例 2:

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

提示:

  • 1 <= n <= 105
  • nums.length == n + 1
  • 1 <= nums[i] <= n
  • nums 中 只有一个整数 出现 两次或多次 ,其余整数均只出现 一次

进阶:

  • 如何证明 nums 中至少存在一个重复的数字?
  • 你可以设计一个线性级时间复杂度 O(n) 的解决方案吗?

来源:力扣(LeetCode)
链接:https://leetcode.cn/problems/find-the-duplicate-number
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

解题思路:

一、暴力【HashSet】

一看到条件说只有一个重复数,就想到了hashset无重复数这个特点,遍历整个数组,如果hashset已存在该数说明遇到重复数,则直接返回当前数。(但是这种方法不满足题目要求的时间复杂度)

java代码:

 1 class Solution {
2 public int findDuplicate(int[] nums) {
3 HashSet<Integer> set = new HashSet<>();
4 for (Integer num : nums){
5 if (set.contains(num)){
6 return num;
7 }else {
8 set.add(num);
9 }
10 }
11 return -1;
12 }
13 }

二、【二分查找】

使用二分查找主要需要弄清楚搜索区间,每一次猜一个数,然后 遍历整个输入数组,进而缩小搜索区间,最后确定重复的是哪个数。

  • 题目中给出数组的长度是:n+1,但是数字是1~n,必然有一个重复数字,应该在数字1~n中搜索,代码中设数组的长度为n,故搜索范围[1, n-1],这里[1,n-1]并不是数组的下标索引,而是数字1~n-1,即左右指针为:left = 1, right = n-1;
  • 在计算出mid以后,统计已知数组中小于等于mid的数的个数count,如果 count 大于 mid,说明重复元素就在区间 [left..mid] 里,否则,由于只存在一个重复元素,于是只能在区间 [mid + 1..right] 里找到;
  • 循环结束的条件是:left == right,这时left 或者right就是我们要找的重复整数。

举例:

[1,2,3,3,4,5,6,7],mid = 3, 小于等于mid的个数count = 4,但是正常小于等于mid的个数应该只有3个(count > mid),说明存在一个重复元素在小于等于mid的范围中,继续在[1,3]去找 (即让right = mid)。

[1,2,3,4,5,6,7,8,8,9],mid=5,小于等于mid的个数count = 5,符合要求(count = 5),题目也说了只存在一个重复元素,mid前面不存在重复元素,重复元素只能存在mid后面了,继续在[5,9]去找(即让left = mid)

 java代码(left < right):

 1 class Solution {
2 public int findDuplicate(int[] nums) {
3 int n = nums.length;
4 int left = 0, right = n - 1;
5 while (left < right){
6 int mid = left + (right - left) / 2;
7 int count = 0;
8 for (int num : nums){
9 if (num <= mid){
10 count++;
11 }
12 }
13 if (count > mid){
14 right = mid;
15 }else{
16 left = mid + 1;
17 }
18 }
19 return left;
20 }
21 }

 python3代码(left <= right):

 1 class Solution:
2 def findDuplicate(self, nums: List[int]) -> int:
3 left, right = 1, len(nums) - 1
4 while left <= right:
5 mid = left + (right - left) // 2
6 count = 0
7 for num in nums:
8 if num < mid:
9 count += 1
10 if count >= mid:
11 right = mid - 1
12 else:
13 left = mid + 1
14 return right

力扣287(java&python)-寻找重复数(中等)的更多相关文章

  1. 力扣(LeetCode)寻找数组的中心索引 个人题解

    给定一个整数类型的数组 nums,请编写一个能够返回数组“中心索引”的方法. 我们是这样定义数组中心索引的:数组中心索引的左侧所有元素相加的和等于右侧所有元素相加的和. 如果数组不存在中心索引,那么我 ...

  2. 287. 寻找重复数 Java解法

    287. 寻找重复数 这题的难点就在于下面的说明了,我们先不管下面的那些说明的要求,用常规的解法来解答下上的题目. 排序思想解法 先把原来的数组进行排序,然后逐个遍历,一旦发现后一个元素和当前的元素相 ...

  3. Java实现 LeetCode 287 寻找重复数

    287. 寻找重复数 给定一个包含 n + 1 个整数的数组 nums,其数字都在 1 到 n 之间(包括 1 和 n),可知至少存在一个重复的整数.假设只有一个重复的整数,找出这个重复的数. 示例 ...

  4. 力扣 -- 寻找两个有序数组的中位数 Median of Two Sorted Arrays python实现

    题目描述: 中文: 给定两个大小为 m 和 n 的有序数组 nums1 和 nums2. 请你找出这两个有序数组的中位数,并且要求算法的时间复杂度为 O(log(m + n)). 你可以假设 nums ...

  5. LeetCode:寻找重复数【287】

    LeetCode:寻找重复数[287] 题目描述 给定一个包含 n + 1 个整数的数组 nums,其数字都在 1 到 n 之间(包括 1 和 n),可知至少存在一个重复的整数.假设只有一个重复的整数 ...

  6. Leetcode之二分法专题-287. 寻找重复数(Find the Duplicate Number)

    Leetcode之二分法专题-287. 寻找重复数(Find the Duplicate Number) 给定一个包含 n + 1 个整数的数组 nums,其数字都在 1 到 n 之间(包括 1 和  ...

  7. LeetCode 第 287 号问题:寻找重复数,一道非常简单的数组遍历题,加上四个条件后感觉无从下手

    今天分享的题目来源于 LeetCode 第 287 号问题:寻找重复数. 题目描述 给定一个包含 n + 1 个整数的数组 nums,其数字都在 1 到 n 之间(包括 1 和 n),可知至少存在一个 ...

  8. LeetCode(力扣)——Search in Rotated Sorted Array2 搜索旋转排序数组 python实现

    题目描述: python实现 Search in Rotated Sorted Array2 搜索旋转排序数组   中文: 假设按照升序排序的数组在预先未知的某个点上进行了旋转. ( 例如,数组 [0 ...

  9. LeetCode(力扣)——Search in Rotated Sorted Array 搜索旋转排序数组 python实现

    题目描述: python实现 Search in Rotated Sorted Array 搜索旋转排序数组   中文:假设按照升序排序的数组在预先未知的某个点上进行了旋转. ( 例如,数组 [0,1 ...

  10. 寻找下一个结点 牛客网 程序员面试金典 C++ java Python

    寻找下一个结点 牛客网 程序员面试金典 C++ java Python 题目描述 请设计一个算法,寻找二叉树中指定结点的下一个结点(即中序遍历的后继). 给定树的根结点指针TreeNode* root ...

随机推荐

  1. Navicat 15下载教程

    Navicat 15下载_永久激活注册码(附图文安装教程) 欢迎关注博主公众号「java大师」, 专注于分享Java领域干货文章, 关注回复「资源」, 免费领取全网最热的Java架构师学习PDF, 转 ...

  2. Kotlin 集合对象的单条件和多条件排序

    原文: Kotlin 集合对象的单条件和多条件排序 - Stars-One的杂货小窝 本文不是太难的东西,因为sortedWith之前没怎么用过,所以就记录下 平常开发经常使用到List,Map等数据 ...

  3. Linux下编译成静态库和动态库,引入到项目中

    目录 配置全局变量 编译动态库和静态库: 动态库编译 静态库编译 AS mk 方式加载静态库和动态库 配置build.gradle 加载静态库方法 将libget.a考入到项目中 配置Android. ...

  4. Ubuntu 14.04 Intel 处理器 硬编解码配置(Intel® Media Server Studio)

    PS:要转载请注明出处,本人版权所有. PS: 这个只是基于<我自己>的理解, 如果和你的原则及想法相冲突,请谅解,勿喷. 前置说明   本文作为本人csdn blog的主站的备份.(Bl ...

  5. 不要升级!不要升级!MacOS 14.4 引发Java 应用崩溃

    如果最近您收到了MacOS 14.4的升级提醒,那么建议你暂时先不要升级! 在x上,Java开发领域的一些大v们,也发现了这个问题,并提醒大家不要升级. 根据Java官方发布的文章了解到,该问题主要是 ...

  6. Linux文件查找、三剑客、正则表达式

    Linux文件查找 1.find查找概述 为什么要有文件查找,因为很多时候我们可能会忘了某个文件所在的位置,此时就需要通过find来查找. find命令可以根据不同的条件来进行查找文件,例如:文件名称 ...

  7. Android线程池封装库

    目录介绍 1.遇到的问题和需求 1.1 遇到的问题有哪些 1.2 遇到的需求 1.3 多线程通过实现Runnable弊端 1.4 为什么要用线程池 2.封装库具有的功能 2.1 常用的功能 3.封装库 ...

  8. 三维模型3DTILE格式轻量化压缩主要技术方法浅析

    三维模型3DTILE格式轻量化压缩主要技术方法浅析 三维模型3DTILE格式轻量化压缩主要技术方法浅析 随着三维地理空间数据的应用日益广泛,为了更快速地传输和存储这些大规模数据,3DTile格式的轻量 ...

  9. Ubuntu安装OpenOffice

    版权声明:本文为博主原创文章,遵循 CC 4.0 by-sa 版权协议,转载请附上原文出处链接和本声明. 本文链接:https://blog.csdn.net/quantum7/article/det ...

  10. 使用 NocoDB 一键将各种数据库转换为智能表格

    NocoDB 是一款开源的无代码数据库平台,可以进行数据管理和应用开发.它的灵感来自 Airtable,支持与 Airtable 类似的电子表格式交互.关系型数据库 Schema 设计.API 自动生 ...