【数据结构】数组复习-二分查找法

news2024/9/25 3:28:32

写这篇博客的起因:

刚开始刷力扣,发现没有一个很好的做题方法,在网络上发现了这个博主的评论,如下。感觉挺适合我,所以开始复习一下数据结构。

c++基础主要是看:

  • 1.bilibili上青岛大学王卓第02周03--2.3线性表的类型定义_哔哩哔哩_bilibili的视频(c++)。

刷题主要是看:

  • 2.leetcode-代码随想录相关手把手带你撕出正确的二分法 | 二分查找法 | 二分搜索法 | LeetCode:704. 二分查找_哔哩哔哩_bilibili

  • 3.leetcode-labuladong系列

《labuladong 的算法笔记》纸质书 | labuladong 的算法笔记

一、数组-二分法

问题1:左闭右闭,左闭右开,左开右闭

一般使用左闭右闭和左闭右开比较多

1:左闭右开(left<right)

left=0
right=len(num)-1
m1 = (right - left) // 2 + left
while(left<right):
    m1>t,right=m1
    m1<t,left=m1+1
    m1=t,m1

2:左闭右闭(left<=right)

left=0
right=len(num)-1
m1 = (right - left) // 2 + left
while(left<=right):
    m1>t,right=m1-1
    m1<t,left=m1+1
    m1=t,m1

二、力扣相关例题

704题:二分查找

python语言-左闭右开

from typing import List

class Solution:
    def search(self, nums: List[int], target: int) -> int:

    # self: 这是一个特殊的参数,用来引用类的实例本身。在类方法中,self 是必须的,但在调用方法时通常不需要显式传入,Python会自动处理。
    # nums: List[int]: 这是函数的第一个参数,命名为 nums,类型注解指示它应该是一个整数列表。
    # target: int: 这是函数的第二个参数,命名为 target,类型注解指示它应该是一个整数。
    # -> int: 这部分指定了函数的返回类型,即该函数会返回一个整数。

        left, right = 0, len(nums)

        while left < right:
            middle = left + (right - left) // 2

            if nums[middle] > target:
                right = middle
            elif nums[middle] < target:
                left = middle + 1
            else:
                return middle

        return -1

def main():
    # Example usage:
    nums = [-1, 0, 3, 5, 9, 12]
    target = 9
    solution = Solution()
    result = solution.search(nums, target)
    print(f"Index of {target} in {nums}: {result}")

if __name__ == "__main__":
    main()

python语言-左闭右闭

from typing import List

class Solution:
    def search(self, nums: List[int], target: int) -> int:

    # self: 这是一个特殊的参数,用来引用类的实例本身。在类方法中,self 是必须的,但在调用方法时通常不需要显式传入,Python会自动处理。
    # nums: List[int]: 这是函数的第一个参数,命名为 nums,类型注解指示它应该是一个整数列表。
    # target: int: 这是函数的第二个参数,命名为 target,类型注解指示它应该是一个整数。
    # -> int: 这部分指定了函数的返回类型,即该函数会返回一个整数。

        left, right = 0, len(nums) - 1  # 定义target在左闭右闭的区间里,[left, right]

        while left <= right:
            middle = left + (right - left) // 2
            
            if nums[middle] > target:
                right = middle - 1  # target在左区间,所以[left, middle - 1]
            elif nums[middle] < target:
                left = middle + 1  # target在右区间,所以[middle + 1, right]
            else:
                return middle  # 数组中找到目标值,直接返回下标
        return -1  # 未找到目标值

def main():
    # Example usage:
    nums = [-1, 0, 3, 5, 9, 12]
    target = 9
    solution = Solution()
    result = solution.search(nums, target)
    print(f"Index of {target} in {nums}: {result}")

if __name__ == "__main__":
    main()

c++语言-左闭右开

# include <vector>

class Solution {
public:
    int search(std::vector<int>& nums, int target) {
        int left = 0;
        int right = nums.size(); // right is the index just beyond the end of the vector

        while (left < right) {
            int middle = left + (right - left) / 2;

            if (nums[middle] > target) {
                right = middle; // target in left half, [left, middle)
            } else if (nums[middle] < target) {
                left = middle + 1; // target in right half, [middle + 1, right)
            } else {
                return middle; // target found at index middle
            }
        }

        return -1; // target not found
    }
};

// Example usage
#include <iostream>

int main() {
    Solution solution;
    std::vector<int> nums = {-1, 0, 3, 5, 9, 12};
    int target = 9;
    int result = solution.search(nums, target);
    std::cout << "Index of " << target << " in nums: " << result << std::endl;
    return 0;
}

c++语言-左闭右闭

# include <vector>

class Solution {
public:
    int search(std::vector<int>& nums, int target) {
        int left = 0;
        int right = nums.size(); // right is the index just beyond the end of the vector

        while (left <= right) {
            int middle = left + (right - left) / 2;

            if (nums[middle] > target) {
                right = middle-1; // target in left half, [left, middle)
            } else if (nums[middle] < target) {
                left = middle + 1; // target in right half, [middle + 1, right)
            } else {
                return middle; // target found at index middle
            }
        }

        return -1; // target not found
    }
};

// Example usage
#include <iostream>

int main() {
    Solution solution;
    std::vector<int> nums = {-1, 0, 3, 5, 9, 12};
    int target = 9;
    int result = solution.search(nums, target);
    std::cout << "Index of " << target << " in nums: " << result << std::endl;
    return 0;
}

相关题目:

35题:搜索插入位置


#
# @lc app=leetcode.cn id=35 lang=python
#
# [35] 搜索插入位置
#

# @lc code=start
from typing import List
class Solution():
    def searchInsert(self, nums: List[int], target: int) -> int:
        """
        :type nums: List[int]
        :type target: int
        :rtype: int
        """
        left = 0

        right = len(nums)  # 左闭右开区间 [left, right)

        while left < right:  # 区间不为空

            # 循环不变量:

            # nums[left-1] < target

            # nums[right] >= target

            mid = left + (right - left) // 2

            if nums[mid] < target:

                left = mid + 1  # 范围缩小到 [mid+1, right)

            else:

                right = mid  # 范围缩小到 [left, mid)

        return left  # 或者 right


def main():
    nums = [-1, 0, 3, 5, 9, 12]
    target = 8
    solution = Solution()
    result = solution.searchInsert(nums, target)
    print(f"Index of {target} in {nums}: {result}")       

if __name__ == "__main__":
    main()


# @lc code=end


34题:在排序数组中查找元素的第一个和最后一个位置

#
# @lc app=leetcode.cn id=34 lang=python
#
# [34] 在排序数组中查找元素的第一个和最后一个位置
#

# @lc code=start
from typing import List

class Solution:
    def searchRange(self, nums: List[int], target: int) -> List[int]:
        left = 0
        right = len(nums) - 1
        result = [-1, -1]

        # Edge case: empty list
        if not nums:
            return result

        # Binary search for the left boundary of target
        while left <= right:
            middle = left + (right - left) // 2
            if nums[middle] < target:
                left = middle + 1
            else:
                right = middle - 1
        # After the loop, `left` is the index of the first occurrence of `target`
        if left < len(nums) and nums[left] == target:
            result[0] = left
        else:
            return result

        # Binary search for the right boundary of target
        left = 0
        right = len(nums) - 1
        while left <= right:
            middle = left + (right - left) // 2
            if nums[middle] <= target:
                left = middle + 1
            else:
                right = middle - 1
        # After the loop, `right` is the index of the last occurrence of `target`
        result[1] = right

        return result

def main():
    nums = [-1, 0, 3, 5, 9, 9, 12]
    target = 10
    solution = Solution()
    result = solution.searchRange(nums, target)
    print(f"Indices of {target} in {nums}: {result}")

if __name__ == "__main__":
    main()
c++
#include <iostream>
#include <vector>
using namespace std;

class Solution {
public:
    vector<int> searchRange(vector<int>& nums, int target) {
        vector<int> result = {-1, -1};
        int left = 0;
        int right = nums.size() - 1;

        // First binary search to find the leftmost index of target
        while (left <= right) {
            int mid = left + (right - left) / 2;
            if (nums[mid] < target) {
                left = mid + 1;
            } else if (nums[mid] > target) {
                right = mid - 1;
            } else {
                // Found target, adjust right to search left part
                result[0] = mid;
                right = mid - 1;
            }
        }

        // Second binary search to find the rightmost index of target
        left = 0;
        right = nums.size() - 1;
        while (left <= right) {
            int mid = left + (right - left) / 2;
            if (nums[mid] < target) {
                left = mid + 1;
            } else if (nums[mid] > target) {
                right = mid - 1;
            } else {
                // Found target, adjust left to search right part
                result[1] = mid;
                left = mid + 1;
            }
        }

        return result;
    }
};

int main() {
    vector<int> nums = {-1, 0, 3, 5, 9, 9, 9, 12};
    int target = 9;
    Solution solution;
    vector<int> result = solution.searchRange(nums, target);
    cout << "Indices of " << target << " in nums: [" << result[0] << ", " << result[1] << "]" << endl;
    return 0;
}

367题:有效的完全平方数

#include <iostream>
using namespace std;

bool isPerfectSquare(int num) {
    if (num == 0 || num == 1) {
        return true;
    }
    long left = 1;
    long right = num;
    long mid = 0;
    while (left <= right) {
        mid = (left + right + 1) / 2; // 保证处理到右边界
        long long res = mid * mid; // 使用 long long 来存放结果,避免整数溢出
        if (res == num) {
            return true;
        } else if (res > num) {
            // [left, mid-1] 区间继续找
            right = mid - 1;
        } else {
            // [mid+1, right] 区间继续找
            left = mid + 1;
        }
    }
    return false;
}

int main() {
    // 测试数据
    int nums[] = {16, 14, 25, 0, 1, 100, 99};
    int n = sizeof(nums) / sizeof(nums[0]);

    for (int i = 0; i < n; ++i) {
        cout << "Number " << nums[i] << (isPerfectSquare(nums[i]) ? " is" : " is not") << " a perfect square." << endl;
    }

    return 0;
}
#include <iostream>
using namespace std;

bool isPerfectSquare(int num) {
    if (num == 0 || num == 1) {
        return true;
    }
    long left = 1;
    long right = num;
    long mid = 0;
    while (left <= right) {
        mid = (left + right + 1) / 2; // 保证处理到右边界
        long long res = mid * mid; // 使用 long long 来存放结果,避免整数溢出
        if (res == num) {
            return true;
        } else if (res > num) {
            // [left, mid-1] 区间继续找
            right = mid - 1;
        } else {
            // [mid+1, right] 区间继续找
            left = mid + 1;
        }
    }
    return false;
}

int main() {
    // 测试数据
    int nums[] = {16, 14, 25, 0, 1, 100, 99};
    int n = sizeof(nums) / sizeof(nums[0]);

    for (int i = 0; i < n; ++i) {
        cout << "Number " << nums[i] << (isPerfectSquare(nums[i]) ? " is" : " is not") << " a perfect square." << endl;
    }

    return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1993094.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

算法 二

求中点 LR&#xff0c;可能溢出 除以2&#xff0c;等同于右移一位 递归、递归的时间复杂度 母问题的规模 子问题的规模&#xff0c;且都相等 调用次数 不用展开看&#xff0c;就看一层。 归并排序 时间复杂度降低的原因&#xff1a;没有浪费比较。比如选择排序&#xff…

48天笔试训练错题——day44

目录 选择题 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 编程题 1. 单词倒排 选择题 1. A 类 IP 地址&#xff1a;0.0.0.0 ~ 127.255.255.255 1 字节网络号&#xff0c;3 字节主机号 B 类 IP 地址&#xff1a;128.0.0.0 ~ 191.255.255.255 2…

服务器网络磁盘挂载

一、Ping测试 先测试磁盘网络的连通性 例如&#xff1a;这里申请的网络磁盘是&#xff1a; 127.0.0.1:/shareData ping 127.0.0.1二、挂载 确认连通后&#xff0c;确定需要挂载的目录&#xff0c;这里服务器的挂载目录为&#xff1a;/data/share &#xff08;自主选择创建目录…

【食物链】

题目 代码 #include<bits/stdc.h> using namespace std; const int N 5e410; int n, k; int p[N], d[N]; int find(int x) {if(p[x] ! x){int root find(p[x]);d[x] d[p[x]];p[x] root;}return p[x]; } int main() {ios::sync_with_stdio(0);cin.tie(0);cout.tie(0)…

RaiDrive / Cyberduck 的安装破解

安装完成后&#xff0c;使用方法可以去这里看&#xff1a; Synology DS920 【外网访问】 这篇文章主要是为了解决 RaiDrive 的登录付费和 Cyberduck 的语言 所以可以尽管下载&#xff0c;盘中 RaiDrive 的免登录免费和 Cyberduck 的中文语言是没有问题的 硬盘映射程序 提…

专题 | IAM业界热度不减,2024市场持续井喷(一)

面对无边界、无规则、无差别&#xff08;企业规模&#xff09;的攻防时代&#xff0c;身份安全在网络安全的重要性日益增强。 身份安全是Gartner最近几年来频繁提及的重要未来趋势之一。RSAC 2023上RSA CEO Rohit Ghai 甚至发表了主题为《迫在眉睫的身份危机&#xff09;》的开…

DAMA学习笔记(十二)-数据质量

1.引言 数据管理能力包括为各类应用设计数据模型、安全存储和访问数据、适当地共享数据、从数据中获得知识&#xff0c;以及保障满足业务需求的能力等。但实现数据价值的前提是数据本身是可靠和可信的&#xff0c;换句话说&#xff0c;数据应是高质量的。 导致低质量数据产生的…

聚焦光热型太阳光模拟器助力多晶硅均匀加热

晶圆均匀加热技术综述 晶圆均匀加热是半导体制造过程中的关键技术之一&#xff0c;直接影响着晶圆上各种加工工艺的质量和稳定性。晶圆加热的目的在于化学气相沉积、退火、氧化等工艺中&#xff0c;通过对晶圆进行必要的热处理&#xff0c;以促进或优化后续工艺步骤。不均匀的…

嵌入式软件--C语言项目 客户信息管理系统

考虑到目前C语言的学习是以为嵌入式做基础而进行的&#xff0c;项目所使用到的语法和结构都是嵌入式常用到的&#xff0c;这是较为特殊和针对性的项目&#xff0c;不与其他同名项目作比较。若有参考着谨慎借鉴。 实现一个客户信息管理系统&#xff0c;功能包括添加客户、修改客…

CTFHUB-web-RCE-远程包含

开启题目 点击下面的 phpinfo 跳转之后发现查看到了 PHP版本&#xff0c;根据源码可以感觉到这里有文件包含&#xff0c;查看之后发现 allow 的配置都开着 抓包之后把 GET 换成 POST&#xff0c;构造 payload 发包&#xff0c;发现根目录有一个 flag 文件 <?php system(ls…

关于FOC学习资料的整理

【自制FOC驱动器】深入浅出讲解FOC控制与SVPWM技术 (qq.com)https://mp.weixin.qq.com/s?__bizMzk0NDQxMTY5OA&mid2247493780&idx1&sn53eacd4fd7e452489fc612bcb2b46a75&source41#wechat_redirect 稚晖君写的文章&#xff0c;涉及面很全&#xff0c;很通俗易…

【机器学习】ImageNet的基本概念以及如何使用ImageNet数据集

引言 ImageNet是一个大型的图像数据库&#xff0c;它根据WordNet的层级结构&#xff08;目前仅限于名词&#xff09;组织&#xff0c;其中每个层级节点都由成百上千张图像来描绘。这个项目对计算机视觉和深度学习研究的发展起到了重要作用 文章目录 引言一、ImageNet的基本概念…

ppt转pdf需要怎么转?6个软件教你快速进行文件格式转换

ppt转pdf需要怎么转&#xff1f;6个软件教你快速进行文件格式转换 将PPT转换为PDF格式是许多办公人员和学生常见的需求&#xff0c;尤其是在分享和发布文档时。以下是六款方便且高效的PPT转PDF软件&#xff0c;帮助你快速进行文件格式转换。 迅捷PDF转换器 这是专业的PDF编辑…

Gartner发布CNAPP云原生应用保护平台市场指南:CNAPP应该具有的4项强制功能和14项通用功能

CNAPP 满足了云原生应用程序和基础设施从开发到生产的全生命周期保护需求。负责云安全策略的安全和风险管理领导者应利用这项研究来分析和评估新兴的 CNAPP 产品。 主要发现 云原生应用和基础设施的攻击面不断扩大&#xff0c;攻击者将攻击重点放在运行时环境&#xff0c;包括网…

Java面试题--JVM大厂篇之全面掌握Parallel GC参数配置:实战指南

目录 引言&#xff1a; 正文&#xff1a; 一、Parallel GC概述 二、Java工程师的痛点 三、Parallel GC参数配置详解 1. 基本参数 2. 新生代参数 3. 老年代参数 4. 调优参数 四、实战案例 案例一&#xff1a;电商网站高并发场景 案例二&#xff1a;金融系统低延迟要…

python 文件打开、读、关闭练习

一、题目要求 二、代码实现 f open("D:\\workspace\\word.txt" , "r", encoding "UTF-8")# 方案一 # content f.read() # count content.count("itheima") # print(f"itmeiha在文件中出现了&#xff1a;{count}次")# 方案…

AI智能助手商业系统软件源码(IMYAI智能助手) AI换脸/智能体GPTs应用/AI视频生成/AI绘画/文档分析/GPT-4o模型支持

人工智能技术的发展日新月异&#xff0c;从深度学习到自然语言处理&#xff0c;再到计算机视觉等领域&#xff0c;不断推动着各行各业的变革。在应用层面&#xff0c;人工智能已深入到内容创作领域&#xff0c;为创作者提供了前所未有的便利和可能性。这些技术的发展潜力巨大&a…

iFC 原理与使用 VoNR 中的 T-ADS

目录 1. iFC 原理与使用 1.01 主要内容 1.02 什么是iFC 1.03 S-CSCF 怎么得到iFC&#xff1f;iFC在哪里定义&#xff1f; 1.04 Cx-User-Data AVP 举例(含iFC) ​编辑 1.05 iFC 具体构成 1.06 iFC 的重要参数&#xff1a;SessionCase 1.07 iFC 实战讲解1&#xff1a;VoN…

【Material-UI】Button 组件中的颜色设置(Color)详解

文章目录 一、基础颜色选项1. Secondary 颜色2. Success 颜色3. Error 颜色 二、定制颜色1. 添加自定义颜色2. 禁用默认颜色 三、高级用法和最佳实践1. 确保对比度2. 语义化颜色3. 考虑用户体验 四、总结 在用户界面设计中&#xff0c;颜色不仅仅是美学的一部分&#xff0c;更是…

【C++ Primer Plus】学习笔记 4

文章目录 前言一、结构类型1.在程序中使用结构2.C11结构初始化3. 结构可以将 string 类作为成员吗4.其他特性5.结构数组 二、共用体三、枚举1.设置枚举量的值2. 枚举的取值范围 前言 该笔记内容为书第四章——复合类型&#xff0c;加油加油 一、结构类型 结构是用户定义的类型…