LeetCode雙指針:有序數組中的單一元素

LeetCode雙指針:有序數組中的單一元素

題目描述

給你一個僅由整數組成的有序數組,其中每個元素都會出現兩次,唯有一個數只會出現一次。

請你找出并返回只出現一次的那個數。

你設計的解決方案必須滿足 O(log n) 時間復雜度和 O(1) 空間復雜度。

示例 1:

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

示例 2:

輸入: nums =  [3,3,7,7,10,11,11]
輸出: 10

解題思路

由有序數組,以及要求 O(log n) 時間復雜度和 O(1) 空間復雜度得知需使用二分查找,怎么找?考慮到它的總數一定是為奇數,那么就可以從左右兩邊每次劃分后的數量進行查找,怎么判別獲得中間值之后知道哪一邊是幾十個哪一邊是偶數個?這個我用的笨方法:舉例

  • 1、[1,1,2,3,3,4,4]右指針為6,左指針為0,除以2之后mid為3(奇數)落在第一個3上,根據預想需要調整右指針到第二個3上

  • 2、[1,1,2,2,3,3,4]右指針為6,左指針為0,除以2之后mid為3(奇數)落在第二個2上,根據預想需要調整左指針到第一個2上

  • 3、[1,2,2,3,3]右指針為4,左指針為0,除以2之后mid為2(偶數)落在第二個2上,根據預想需要調整右指針到第二個2上

  • 4、[1,1,2,2,3]右指針為4,左指針為0,除以2之后mid為2(偶數)落在第一個2上,根據預想需要調整左指針到第一個2上

可能此種解釋比較麻煩,我也沒找到讓自己和解的方法,僅代表我自己的理解

接下來就是進行歸類,我把需要移動左指針的進行歸類(1,3)先進行假設:

    1. 若mid為奇數判斷它和它前一個是否相等,相等則左指針調整
    1. 若mid為偶數判斷它和它后一個是否相等,相等則左指針調整

帶入2,4情況,發現符合,可以試試找規律,自己推出來較為容易理解,上述也可以不知道這一種選擇,改變判等的位置,相應更改后邊即可

代碼

public class BinSearch3 {public int singleNonDuplicate(int[] nums) {int low = 0, high = nums.length - 1;while (low < high) {int mid = (high - low) / 2 + low;//若mid為偶數判斷它和它后一個是否相等,相等則左指針調整if (mid%2==0){if (nums[mid] == nums[mid + 1]){low = mid + 1;}else {high = mid;}//若mid為奇數判斷它和它前一個是否相等,相等則左指針調整}else {if (nums[mid] == nums[mid - 1]){low = mid + 1;}else {high = mid;}}}return nums[low];}public static void main(String[] args) {BinSearch3 b=new BinSearch3();System.out.println(b.singleNonDuplicate(new int[]{1,1,2,3,3,4,4}));}
}

代碼優化

如上,判定奇偶情況代碼十分臃腫,冗余,對其進行進一步改進,此時需要了解^的使用

位運算的異或操作符 ^。二進制中,異或有一個有趣的性質,即 a ^ bab 不相同時結果為 1,相同時結果為 0。

1 ^ 3 的結果是 01 ^ 11 = 10,即十進制中的 2

帶入上述例子[1,1,2,2,3,3,4]mid=3,為奇數將2和1進行異或 01 ^ 11 = 10即十進制中的 2那么不正是相當于對其進行了減一操作

同理,當mid=2時,01 ^ 10 = 11即十進制中的 3那么不正是相當于對其進行了加一操作

因此對其進行優化后:

public class BinSearch3 {public int singleNonDuplicate(int[] nums) {int low = 0, high = nums.length - 1;while (low < high) {int mid = (high - low) / 2 + low;if (nums[mid] == nums[mid ^ 1]) {low = mid + 1;} else {high = mid;}}return nums[low];}public static void main(String[] args) {BinSearch3 b = new BinSearch3();System.out.println(b.singleNonDuplicate(new int[]{1, 1, 2, 3, 3, 4, 4, 8, 8}));}
}

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/208176.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/208176.shtml
英文地址,請注明出處:http://en.pswp.cn/news/208176.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

關于什么是 JVM

關于什么是 JVM&#xff0c;看看普通?和??的回答。 普通人 JVM 就是 Java 虛擬機&#xff0c;是?來運?我們平時所寫的 Java 代碼的。優點是它會 ?動進?內存管理和垃圾回收&#xff0c;缺點是?旦發?問題&#xff0c;要是不了解 JVM 的運? 機制&#xff0c; 就很難…

是誰還沒玩AI擴圖?快跟上節奏啦

最近&#xff0c;抖音上的AI擴圖突然火了&#xff0c;看完真的讓人笑掉大牙&#xff5e;&#xff5e;&#xff5e; 這一熱議的話題#AI擴圖#在短視頻平臺抖音上的播放量已經突破7.8億次&#xff0c;而相關的討論也如同星火燎原&#xff0c;迅速點燃了公眾的好奇心。從“用AI擴圖…

中偉視界:皮帶跑偏、異物檢測AI算法除了礦山行業應用,還能在鋼鐵、火電、港口等行業中使用嗎?

隨著工業化的發展&#xff0c;皮帶輸送機已經成為各行業中不可或缺的重要設備&#xff0c;但是在使用過程中&#xff0c;由于各種原因&#xff0c;皮帶常常出現跑偏問題&#xff0c;給生產運營帶來了諸多困擾。不僅僅是礦山行業&#xff0c;鋼鐵、火電、港口等行業也都面臨著皮…

C語言 掃雷游戲

代碼在一個項目里完成&#xff0c;分成三個.c.h文件(game.c,game.h,main.c) 在Clion軟件中通過運行調試。 /大概想法/ 主函數main.c里是大框架(菜單,掃雷棋盤初始化&#xff0c;隨機函數生成雷&#xff0c;玩家掃雷) game.h函數聲明(除main函數和游戲函數外的一些函數聲明) ga…

RepidJson將內容寫入文件

使用 RapidJSON 將內容寫入文件的步驟如下&#xff1a; 創建一個 rapidjson::Document 對象&#xff0c;將需要寫入文件的內容存儲到其中。創建一個 rapidjson::StringBuffer 對象來保存 JSON 字符串。將 rapidjson::Document 對象轉換為 JSON 字符串&#xff0c;并將其放入 r…

日志打印傳值 傳引用 右值引用性能測試

結論 ubuntu x86平臺qnx平臺優化傳值都是比傳引用的差 但是差距很小 測試代碼 #include <cstdint> #include <ctime> #include <string>#ifdef __linux__#define ITERATIONS 10000000 #else#define ITERATIONS 100000 #endiftemplate <typename... AR…

rust高級 異步編程 一 future

文章目錄 Async 編程簡介async/.await 簡單入門 Future 執行器與任務調度Future 特征使用 Waker 來喚醒任務構建一個定時器執行器 Executor構建執行器 完整代碼 Async 編程簡介 OS 線程, 它最簡單&#xff0c;也無需改變任何編程模型(業務/代碼邏輯)&#xff0c;因此非常適合作…

Linux設置root初始密碼

目錄 一、Linux系統中普通用戶和特權用戶&#xff08;root&#xff09; 二、Linux系統中設置root初始密碼 一、Linux系統中普通用戶和特權用戶&#xff08;root&#xff09; windows 系統中有普通用戶和特權用戶&#xff0c;特權用戶是 administer&#xff0c;普通用戶可以…

mybatisplus調用oracle存儲過程

mybatisplus調用oracle存儲過程 創建一個測試的oracle存儲過程 -- 創建攜帶返回值存儲過程 CREATE OR REPLACE PROCEDURE SP_SUM_PROC_2023(number1 IN NUMBER, number2 IN NUMBER, result OUT NUMBER,result2 OUT NUMBER) is BEGIN result : number1 number2; result2 : 99…

微服務01

筆記&#xff1a; day03-微服務01 - 飛書云文檔 (feishu.cn) 數據庫連接不上&#xff1f; 要在虛擬機啟動MySQL容器。docker start mysql 服務治理 服務提供者&#xff1a;暴露服務接口&#xff0c;供其他服務調用 服務消費者&#xff1a;調用其他服務提供的接口 注冊中心&…

Java IO流(一) 基本知識

Java IO流 一、基礎知識 IO流即存儲和讀取數據的解決方案。 &#xff08;一&#xff09;File 表示系統中的文件或者文件夾的路徑 獲取文件信息(大小&#xff0c;文件名&#xff0c;修改時間) 創建文件/文件夾 刪除文件/文件夾 判斷文件的類型 注意&#xff1a;File類只能對…

STL(五)(queue篇)

我發現之前一版在電腦上看 常用函數部分 沒有問題,由于是手打上去的,在手機上看會發生錯位問題,現已將電腦原版 常用函數部分 截圖改為圖片形式,不會再發生錯位問題,非常感謝大家的支持 ### priority_queue優先隊列出現頻率非常高,尤為重要(是一定要掌握的數據結構) 1.queue隊…

A : DS靜態查找之順序查找

Description 給出一個隊列和要查找的數值&#xff0c;找出數值在隊列中的位置&#xff0c;隊列位置從1開始 要求使用帶哨兵的順序查找算法 Input 第一行輸入n&#xff0c;表示隊列有n個數據 第二行輸入n個數據&#xff0c;都是正整數&#xff0c;用空格隔開 第三行輸入t&…

Spring-retry失敗重試機制

提示&#xff1a;文章寫完后&#xff0c;目錄可以自動生成&#xff0c;如何生成可參考右邊的幫助文檔 文章目錄 前言一、引入依賴二、主啟動類上加EnableRetry三、Server層注意 四、失敗后回調方法總結 前言 提示&#xff1a;SpringBoot項目為例 原文鏈接&#xff1a;https://…

docker全解

docker全解 一、docker的基本概念 什么是docker? docker是一個開源的應用容器引擎&#xff0c;讓開發者可以打包他們的應用以及依賴包到一個可移植的鏡像中&#xff0c;然后發布到任何流行的Linux或Windows機器上&#xff0c;也可以實現虛擬化。容器是完全使用沙箱機制&#…

MIT線性代數筆記-第26講-對稱矩陣及正定性

目錄 26.對稱矩陣及正定性打賞 26.對稱矩陣及正定性 實對稱矩陣的特征值均為實數&#xff0c;并且一定存在一組兩兩正交的特征向量 這對于單位矩陣顯然成立 證明特征值均為實數&#xff1a; ? ???設一個對稱矩陣 A A A&#xff0c;對于 A x ? λ x ? A \vec{x} \lambda…

作業12.8

1. 使用手動連接&#xff0c;將登錄框中的取消按鈕使用qt4版本的連接到自定義的槽函數中&#xff0c;在自定義的槽函數中調用關閉函數。將登錄按鈕使用qt5版本的連接到自定義的槽函數中&#xff0c;在槽函數中判斷ui界面上輸入的賬號是否為"admin"&#xff0c;密碼是…

Matlab simulink PLL學習筆記

本文學習內容&#xff1a;【官方】2022小邁步之 MATLAB助力芯片設計系列&#xff08;一&#xff09;&#xff1a;電路仿真與模數混合設計基礎_嗶哩嗶哩_bilibili 時域模型 testbench搭建 菜單欄點擊simulink 創建空白模型 點擊庫瀏覽器 在PLL里面選擇一種架構拖拽到畫布。 如…

一文理解什么是交叉熵損失函數以及它的作用

今天看一個在深度學習中很枯燥但很重要的概念——交叉熵損失函數。 作為一種損失函數&#xff0c;它的重要作用便是可以將“預測值”和“真實值(標簽)”進行對比&#xff0c;從而輸出 loss 值&#xff0c;直到 loss 值收斂&#xff0c;可以認為神經網絡模型訓練完成。 那么這…

【Java用法】Hutool樹結構工具-TreeUtil快速構建樹形結構的兩種方式 + 數據排序

Hutool樹結構工具-TreeUtil快速構建樹形結構的兩種方式 數據排序 一、業務場景二、Hutool官網樹結構工具2.1 介紹2.2 使用2.2.1 定義結構2.2.2 構建Tree2.2.3 自定義字段名 2.3 說明 三、具體的使用場景3.1 實現的效果3.2 業務代碼3.3 實現自定義字段的排序 四、踩過的坑4.1 坑…