当前位置: 首页 > news >正文

[C语言][C++][时间复杂度详解分析]二分查找——杨氏矩阵查找数字详解!!!

一,题目

遇到的一道算法题:

1,已知有一个数字矩阵(row行,col列),矩阵的每行 从左到右 递增,每列 从上到下 递增。

2,现输入一个数字  num  ,判断数字矩阵中是否存在该元素,若存在,求出此数字在矩阵的哪一行,哪一列?(求出其中一组行列即可)

3,要求:时间复杂度小于O(N)。

二,简介杨氏矩阵

此题目中的矩阵也叫做杨氏矩阵,通常可以用二维数组来表示。

杨氏矩阵画图举例:

解决此题并不需要深刻理解杨氏矩阵。

但若有需要,杨氏矩阵详解链接附上:杨氏矩阵 - OI Wiki (oi-wiki.org)

三,各种解法(时间复杂度的详解)以及思考

3.1:暴力遍历

   3.1.1:详解代码

for (int i = 0; i < row; i++)
{for (int j = 0; j < col; j++){if (Y_arr[i][j] == search){printf("%d %d\n", i, j);}}
}

   3.1.2:时间复杂度分析

   最坏的情况下,此方法的时间复杂度为 O(rwo * col)

   不符合题目要求。

   优化!

3.2:对每行元素进行二分查找

   3.2.1:在代码中具体分析!

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#define NUM 10
int main()
{int Y_arr[NUM][NUM] = { 0 };int row = 0;int col = 0;//输入行 列scanf("%d %d", &row, &col);//输入数组中的元素for (int i = 0; i < row; i++){for (int j = 0; j < col; j++){scanf("%d", &Y_arr[i][j]);}}//输入要查找的数int search = 0;scanf("%d", &search);//开始查找for (int i = 0; i < row; i++){int left = 0;int right = col - 1;while (left <= right){int mid = left + (right - left) / 2;if (Y_arr[i][mid] < search)//中数小于要查找的数,更新左下标,缩小范围{left = mid + 1;}else if (Y_arr[i][mid] > search)//中数大于要查找的数,更新右下标,缩小范围{right = mid - 1;}else//找到了{printf("要查找的数的行下标是 %d , 列下标是 %d\n", i, mid);return 0;}}}printf("找不到\n");return 0;
}

   3.2.2:时间复杂度分析

   最坏的情况下,此方法的时间复杂度是 O( row * log(col) )

   仍不符合题目要求。

   再优化!

3.3:定位查找法

   3.3.1:规律总结

      每次从右上角开始查找:

      Ⅰ:若要查找的数大于每次的右上角的数,就更新行数。

      Ⅱ:若要查找的数小于每次的右上角的数,就更新列数。

   3.3.2:画图分析 | 模拟查找

   

   3.3.3:代码解决

   

​
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#define NUM 10
int main()
{int Y_arr[NUM][NUM] = { 0 };int row = 0;int col = 0;//输入行 列scanf("%d %d", &row, &col);//输入数组中的元素for (int i = 0; i < row; i++){for (int j = 0; j < col; j++){scanf("%d", &Y_arr[i][j]);}}//输入要查找的数int search = 0;scanf("%d", &search);//开始查找int temp_row = 0;int temp_col = col - 1;while (temp_row < row && temp_col >= 0){if (Y_arr[temp_row][temp_col] > search){temp_col -= 1;}else if (Y_arr[temp_row][temp_col] < search){temp_row += 1;}else{printf("要查找的数的行下标是 %d , 列下标是 %d\n", temp_row, temp_col);return 0;}}printf("找不到\n");return 0;
}​

   3.3.4:时间复杂度分析

   最坏的情况下,此方法的时间复杂度为 O( row + col ).

   符合题目要求。

   完美!!!

四,总结

4.1:问题解决

   Ⅰ,同一种问题的解决,可能会使用多种方法,尽我们所能地使用最优解,这是再好不过了。    

   Ⅱ,不断地优化代码,不断地学习新方法,时时刻刻在进步

   Ⅲ,欢迎分享,感谢阅读!

 

相关文章:

  • win wsl2 Ubuntu-22.04 设置时间为国内时间
  • 微信小程序如何实现实时显示输入内容
  • C# OpenCvSharp DNN Gaze Estimation 视线估计
  • 桌面型物联网智能机器人设计(预告)
  • uniapp本地存储日志
  • 【Java基础】之进程与线程
  • python每日学19: 类vs字典
  • 如何编写.gitignore文件
  • 万户 ezOFFICE wpsservlet SQL注入漏洞复现
  • 学区块链智能合约?来自培训学校内部的学习计划
  • Pandas处理Excel文件的实用指南 - Python开发技巧XI
  • import sys是什么
  • AR 自回归模型
  • Spring Boot项目中集成连接池及部分细节说明
  • 【开源】JAVA+Vue.js实现大学兼职教师管理系统
  • 网络传输文件的问题
  • Dubbo 整合 Pinpoint 做分布式服务请求跟踪
  • iOS 颜色设置看我就够了
  • Laravel深入学习6 - 应用体系结构:解耦事件处理器
  • leetcode-27. Remove Element
  • Material Design
  • Python语法速览与机器学习开发环境搭建
  • SegmentFault 社区上线小程序开发频道,助力小程序开发者生态
  • 关于for循环的简单归纳
  • 记一次和乔布斯合作最难忘的经历
  • 技术胖1-4季视频复习— (看视频笔记)
  • 精彩代码 vue.js
  • 前端知识点整理(待续)
  • 前嗅ForeSpider采集配置界面介绍
  • 如何用vue打造一个移动端音乐播放器
  • 入门级的git使用指北
  • 小程序上传图片到七牛云(支持多张上传,预览,删除)
  • 用quicker-worker.js轻松跑一个大数据遍历
  • ​马来语翻译中文去哪比较好?
  • #pragam once 和 #ifndef 预编译头
  • #常见电池型号介绍 常见电池尺寸是多少【详解】
  • (ctrl.obj) : error LNK2038: 检测到“RuntimeLibrary”的不匹配项: 值“MDd_DynamicDebug”不匹配值“
  • (阿里巴巴 dubbo,有数据库,可执行 )dubbo zookeeper spring demo
  • (附源码)ssm高校社团管理系统 毕业设计 234162
  • (一)基于IDEA的JAVA基础12
  • (原+转)Ubuntu16.04软件中心闪退及wifi消失
  • (转)Linux NTP配置详解 (Network Time Protocol)
  • (转)机器学习的数学基础(1)--Dirichlet分布
  • ./configure,make,make install的作用(转)
  • ./mysql.server: 没有那个文件或目录_Linux下安装MySQL出现“ls: /var/lib/mysql/*.pid: 没有那个文件或目录”...
  • .Family_物联网
  • .NET/C# 阻止屏幕关闭,阻止系统进入睡眠状态
  • @configuration注解_2w字长文给你讲透了配置类为什么要添加 @Configuration注解
  • @JsonSerialize注解的使用
  • @ModelAttribute使用详解
  • [ vulhub漏洞复现篇 ] GhostScript 沙箱绕过(任意命令执行)漏洞CVE-2019-6116
  • [ vulhub漏洞复现篇 ] JBOSS AS 4.x以下反序列化远程代码执行漏洞CVE-2017-7504
  • [ vulhub漏洞复现篇 ] ThinkPHP 5.0.23-Rce
  • [1] 平面(Plane)图形的生成算法
  • [14]内置对象