代码随想录训练营Day 66|卡码网101.孤岛的总面积、102.沉没孤岛、103.水流问题、104.建造最大岛屿
1.孤岛的总面积
101. 孤岛的总面积 | 代码随想录
代码:(bfs广搜)
#include <iostream>
#include <vector>
#include <queue>
using namespace std;
int dir[4][2] = {1,0,0,1,-1,0,0,-1};
int count;
void bfs(vector<vector<int>>&grid,int x,int y){queue<pair<int,int>> que;que.push({x,y});grid[x][y] = 0; // 这里用grid的元素变为0来进行标记count++;while(!que.empty()){pair<int,int> cur = que.front();que.pop();int curx = cur.first;int cury = cur.second;for(int i = 0; i < 4; i++){int nextx = curx + dir[i][0];int nexty = cury + dir[i][1];if(nextx < 0||nextx >= grid.size()||nexty < 0 ||nexty >= grid[0].size()){continue;}if(grid[nextx][nexty] == 1){que.push({nextx,nexty});grid[nextx][nexty] = 0;count++;}}}
}
int main(){// 输入int n,m;cin >> n >> m;vector<vector<int>> grid(n,vector<int>(m,0));for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){cin >> grid[i][j];}}// 处理for(int i = 0; i < n; i++){if(grid[i][0] == 1) bfs(grid,i,0);if(grid[i][m - 1] == 1) bfs(grid,i,m - 1);}for(int j = 0; j < m; j++){if(grid[0][j] == 1) bfs(grid,0,j);if(grid[n - 1][j] == 1) bfs(grid,n - 1,j);}count = 0;for(int i = 1; i < n - 1; i++){for(int j = 1; j < m - 1; j++){if(grid[i][j] == 1) bfs(grid,i,j);}}// 输出cout << count << endl;
}
思路:基础题型,这次直接在grid表上进行标记。先把靠近陆地的岛屿都标为0。将用于统计面积的变量的count置为0。接下来就可以排除临近陆地的岛屿,只统计孤岛的数量了。
易错点:我又犯错了。先是忘记写命名空间了,然后又是在if判断里二维数组我只写了一个下标,最后是找边界找错了,我的循环变量i是在变的,我只要固定另一个下标为临界值就好了。不知道为什么我把i放到了边界的运算里(。。脑子糊了)
代码:(dfs 深搜)
#include <iostream>
#include <vector>
#include <queue>
using namespace std;
int dir[4][2] = {1,0,0,1,-1,0,0,-1};
int count;
void bfs(vector<vector<int>>&grid,int x,int y){if(grid[x][y] == 0){return;}grid[x][y] = 0;count++;for(int i = 0; i < 4; i++){int nextx = x + dir[i][0];int nexty = y + dir[i][1];if(nextx < 0||nextx >= grid.size()||nexty < 0||nexty >= grid[0].size()){continue;}bfs(grid,nextx,nexty);}
}
int main(){// 输入int n,m;cin >> n >> m;vector<vector<int>> grid(n,vector<int>(m,0));for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){cin >> grid[i][j];}}// 处理for(int i = 0; i < n; i++){if(grid[i][0] == 1) bfs(grid,i,0);if(grid[i][m - 1] == 1) bfs(grid,i,m - 1);}for(int j = 0; j < m; j++){if(grid[0][j] == 1) bfs(grid,0,j);if(grid[n - 1][j] == 1) bfs(grid,n - 1,j);}count = 0;for(int i = 1; i < n - 1; i++){for(int j = 1; j < m - 1; j++){if(grid[i][j] == 1) bfs(grid,i,j);}}// 输出cout << count << endl;
}
思路:我的博客快做成个人错误大赏了。。。
这次的错误是 在进行下标是否非法的判断的时候,我又写错了。一定要注意边界条件啊,以后检查的时候就应该找这种判断语句好好看看。
2.沉没孤岛
102. 沉没孤岛 | 代码随想录
代码:(深搜dfs)
#include <iostream>
#include <vector>
#include <queue>
using namespace std;
int dir[4][2] = {1,0,0,1,-1,0,0,-1};
int count;
void bfs(vector<vector<int>>&grid,int x,int y){if(grid[x][y] == 2||grid[x][y] == 0){return;}grid[x][y] = 2;for(int i = 0; i < 4; i++){int nextx = x + dir[i][0];int nexty = y + dir[i][1];if(nextx < 0||nextx >= grid.size()||nexty < 0||nexty >= grid[0].size()){continue;}bfs(grid,nextx,nexty);}
}
int main(){// 输入int n,m;cin >> n >> m;vector<vector<int>> grid(n,vector<int>(m,0));for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){cin >> grid[i][j];}}// 处理// 将临近陆地的标为2 和 孤岛区分开vector<vector<bool>> visited(n,vector<bool>(m,false));for(int i = 0; i < n; i++){if(grid[i][0] == 1) bfs(grid,i,0);if(grid[i][m - 1] == 1) bfs(grid,i,m - 1);}for(int j = 0; j < m; j++){if(grid[0][j] == 1) bfs(grid,0,j);if(grid[n - 1][j] == 1) bfs(grid,n - 1,j);}// 将孤岛沉没 将临近陆地的单元还原for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){if(grid[i][j] == 1) grid[i][j] = 0;if(grid[i][j] == 2) grid[i][j] = 1;}}// 输出for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){cout << grid[i][j] << " ";}cout << endl;}
}
思路:这里比较巧妙的就是因为临近陆地的岛屿比较好判断,所以将其标记为2,只要与孤岛区别开就好了。接下来,就是把1变为0,把2变为1,输出就好了
3.水流问题
103. 水流问题 | 代码随想录
代码: (深搜dfs)
#include <iostream>
#include <vector>
using namespace std;
int dir[4][2] = {0,1,1,0,0,-1,-1,0};
void dfs(const vector<vector<int>> &grid,vector<vector<bool>> &visited,int x, int y){if(visited[x][y]) return;visited[x][y] = true;for(int i = 0; i < 4; i++){int nextx = x + dir[i][0];int nexty = y + dir[i][4];if(nextx < 0||nextx >= grid.size()||nexty < 0||nexty >= grid[0].size()){continue;}// 必须从低到高if(grid[nextx][nexty] < grid[x][y]) continue;dfs(grid,visited,nextx,nexty);}return;
}
int main(){//输入int n,m;cin >> n >> m;vector<vector<int>> grid(n,vector<int>(m,0));for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){cin >> grid[i][j];}}// 处理vector<vector<bool>> firstBorder(n,vector<bool>(m,false));vector<vector<bool>> secondBorder(n,vector<bool>(m,false));for(int i = 0; i < n; i++){dfs(grid,firstBorder,i,0);dfs(grid,secondBorderBorder,i,m - 1);}for(int j = 0; j < m; j++){dfs(grid,firstBorder,0,j);dfs(grid,secondBorder,n - 1,j);}// 输出for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){if(firstBorder[i][j]&&secondBorder[i][j]){cout << i << j << endl;}}}
}
思路:这道题的优化很巧妙,因为从边界出发好判断,所以直接从边界出发,把边界可以到达的地方而且是递增的单元进行标记。上边界和下边界各用一套标记,当一个单元被标记两次时,就说明它时满足题意的。
易错点:我自己写了半天,忘记写最重要的 if(grid[nextx][nexty] < grid[x][y]) continue;了。
4.建造最大岛屿
104.建造最大岛屿 | 代码随想录
代码:
#include <iostream>
#include <vector>
#include <unordered_set>
#include <unordered_map>
using namespace std;
int count;
int dir[4][2] = {0,1,1,0,0,-1,-1,0};
void dfs(vector<vector<int>>&grid,vector<vector<bool>>&visited,int x,int y,int mark){if(visited[x][y]||grid[x][y] == 0) return;visited[x][y] = true; // 标记已访问grid[x][y] = mark; // 每个岛屿都有对应的标签count++;for(int i = 0; i < 4; i++){int nextx = x + dir[i][0];int nexty = y + dir[i][1];if(nextx < 0||nextx >= grid.size()||nexty < 0||nexty >= grid[0].size()){continue;}dfs(grid,visited,nextx,nexty,mark);}return;
}
int main(){// 输入int n,m;cin >> n >> m;vector<vector<int>> grid(n,vector<int>(m,0));for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){cin >> grid[i][j];}}// 处理vector<vector<bool>> visited(n,vector<bool>(m,false));unordered_map<int,int> gridNum;int mark = 2; // 记录岛屿的编号bool isAllGrid = true; // 记录整个地图是否都是陆地(如果是,就没法添加陆地了)for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){if(grid[i][j] == 0) isAllGrid = false;if(!visited[i][j] && grid[i][j] == 1){count = 0;dfs(grid,visited,i,j,mark);gridNum[mark] = count; // 记录每一个岛屿的面积mark++;}}}if(isAllGrid == true) {cout << n*m << endl;return 0;}// 根据所填陆地,计算周边岛屿面积之和int result = 0;unordered_set<int> visitedGrid; // 标记访问过的岛屿for(int i = 0; i < n; i++){for(int j = 0; j < m; j++){count = 1; // 记录连接后的岛屿数量visitedGrid.clear();if(grid[i][j] == 0){for(int k = 0; k < 4; k++){int nexti = i + dir[k][0];int nextj = j + dir[k][1];if(nexti < 0||nexti >= grid.size()||nextj < 0||nextj >= grid[0].size()){continue;}if(visitedGrid.count(grid[nexti][nextj])) continue; // 添加过的岛屿不要重复添加count += gridNum[grid[nexti][nextj]];visitedGrid.insert(grid[nexti][nextj]);}}result = max(result,count);}}cout << result << endl;
}
思路:这道题是先计算各个岛屿的面积,然后遍历每一块海域,将这块添加的单元与其临近的岛屿面积进行相加求和,保存里面的最大值。
这道题真的是错死我了。。。这个涉及到很多细节,比如要考虑全是陆地的情况,要将每个岛屿进行面积和标号的映射,要在计算连接后的总面积的时候,将统计过的岛屿进行标记。。。我真的,太痛了。
相关文章:
代码随想录训练营Day 66|卡码网101.孤岛的总面积、102.沉没孤岛、103.水流问题、104.建造最大岛屿
1.孤岛的总面积 101. 孤岛的总面积 | 代码随想录 代码:(bfs广搜) #include <iostream> #include <vector> #include <queue> using namespace std; int dir[4][2] {1,0,0,1,-1,0,0,-1}; int count; void bfs(vector<vector<int>>&a…...
根据状态转移写状态机-二段式
目录 描述 输入描述: 输出描述: 描述 题目描述: 如图所示为两种状态机中的一种,请根据状态转移图写出代码,状态转移线上的0/0等表示的意思是过程中data/flag的值。 要求: 1、 必须使用对应类型的状…...
PyTorch C++扩展用于AMD GPU
PyTorch C Extension on AMD GPU — ROCm Blogs 本文演示了如何使用PyTorch C扩展,并通过示例讨论了它相对于常规PyTorch模块的优势。实验在AMD GPU和ROCm 5.7.0软件上进行。有关支持的GPU和操作系统的更多信息,请参阅系统要求(Linux…...
Hadoop archive
Index of /dist/hadoop/commonhttps://archive.apache.org/dist/hadoop/common/...
R语言——R语言基础
1、用repeat、for、while计算从1-10的所有整数的平方和 2、编写一个函数,给出两个正整数,计算他们的最小公倍数 3、编写一个函数,让用户输入姓名、年龄,得出他明年的年龄。用paste打印出来。例如:"Hi xiaoming …...
VFB电压反馈和CFB电流反馈运算放大器(运放)选择指南
VFB电压反馈和CFB电流反馈运算放大器(运放)选择指南 电流反馈和电压反馈具有不同的应用优势。在很多应用中,CFB和VFB的差异并不明显。当今的许多高速CFB和VFB放大器在性能上不相上下,但各有其优缺点。本指南将考察与这两种拓扑结构相关的重要考虑因素。…...
elasticsearch安装(centos7)
先给出网址 elasticsearch:Download Elasticsearch | Elastic elasticKibana:Download Kibana Free | Get Started Now | Elastic Logstash:Download Logstash Free | Get Started Now | Elastic ik分词:Releases infinilabs/…...
Java高手的30k之路|面试宝典|精通JVM(二)
JVM基本结构 类加载子系统:负责将.class文件加载到内存中,并进行验证、准备、解析和初始化。运行时数据区:包括堆(Heap)、方法区(Method Area)、Java栈(Java Stack)、本…...
JVM专题六:JVM的内存模型
前面我们通过Java是如何编译、JVM的类加载机制、JVM类加载器与双亲委派机制等内容了解到了如何从我们编写的一个.Java 文件最终加载到JVM里的,今天我们就来剖析一下这个Java的‘中介平台’JVM里面到底长成啥样。 JVM的内存区域划分 Java虚拟机(JVM&…...
学习java第一百零七天
解释JDBC抽象和DAO模块 使用JDBC抽象和DAO模块,我们可以确保保持数据库代码的整洁和简单,并避免数据库资源关闭而导致的问题。它在多个数据库服务器给出的异常之上提供了一层统一的异常。它还利用Spring的AOP模块为Spring应用程序中的对象提供事务管理服…...
k8s上尝试滚动更新和回滚
滚动更新和回滚 实验目标: 学习如何进行应用的滚动更新和回滚操作。 实验步骤: 创建一个 Deployment。更新 Deployment 的镜像版本,观察滚动更新过程。回滚到之前的版本,验证回滚操作。 今天呢,我们继续来进行我们k…...
GitHub Copilot 登录账号激活,已经在IntellJ IDEA使用
GitHub Copilot 想必大家都是熟悉的,一款AI代码辅助神器,相信对编程界的诸位并不陌生。 今日特此分享一项便捷的工具,助您轻松激活GitHub Copilot,尽享智能编码之便利! GitHub Copilot 是由 GitHub 和 OpenAI 共同开…...
进程知识点(二)
文章目录 一、进程关系?二、孤儿态进程(Orphan)定义危害处理 三、僵尸进程定义处理 四、守护进程(Daemon )定义作用 总结 一、进程关系? 亲缘关系:亲缘关系主要体现于父子进程,子进程父进程创建,代码继承于父进程&…...
【线性代数】【一】1.6 矩阵的可逆性与线性方程组的解
文章目录 前言一、求解逆矩阵二、线性方程组的解的存在性总结 前言 前文我们引入了逆矩阵的概念,紧接着我们就需要讨论一个矩阵逆的存在性以及如何求解这个逆矩阵。最后再回归上最初的线性方程组的解,分析其中的联系。 一、求解逆矩阵 我们先回想一下在…...
基于大型语言模型的全双工语音对话方案
摘要解读 我们提出了一种能够以全双工方式运行的生成性对话系统,实现了无缝互动。该系统基于一个精心调整的大型语言模型(LLM),使其能够感知模块、运动功能模块以及一个具有两种状态(称为神经有限状态机,n…...
Spring Boot集成Minio插件快速入门
1 Minio介绍 MinIO 是一个基于 Apache License v2.0 开源协议的对象存储服务。它兼容亚马逊 S3 云存储服务接口,非常适合于存储大容量非结构化的数据,例如图片、视频、日志文件、备份数据和容器/虚拟机镜像等,而一个对象文件可以是任意大小&…...
【C++新特性】右值引用
右值和右值的区别 C11 中右值可以分为两种:一个是将亡值( xvalue, expiring value),另一个则是纯右值( prvalue, PureRvalue): 纯右值:非引用返回的临时变量、运算表达式产生的临时变…...
信息安全基础知识(完整)
信息安全基础知识 安全策略表达模型是一种对安全需求与安全策略的抽象概念表达,一般分为自主访问控制模型(HRU)和强制访问控制模型(BLP、Biba)IDS基本原理是通过分析网络行为(访问方式、访问量、与历史访问…...
QT
#include "widget.h" #include "ui_widget.h" Widget::Widget(QWidget *parent) : QWidget(parent) , ui(new Ui::Widget) ,Gcancle(new QPushButton("取消",this)) ,EmmEdit(new QLineEdit(this)) { ui->setupUi(this);…...
双例集合(三)——双例集合的实现类之TreeMap容器类
Map接口有两个实现类,一个是HashMap容器类,另一个是TreeMap容器类。TreeMap容器类的使用在API上于HashMap容器类没有太大的区别。它们的区别主要体现在两个方面,一个是底层实现方式上,HashMap是基于Hash算法来实现的吗,…...
从零开发Shell补全脚本:学习git-flow-completion的代码架构
从零开发Shell补全脚本:学习git-flow-completion的代码架构 【免费下载链接】git-flow-completion Bash, Zsh and fish completion support for git-flow. 项目地址: https://gitcode.com/gh_mirrors/gi/git-flow-completion 掌握Shell补全脚本开发是提升命令…...
如何在5分钟内快速安装Homebridge Config UI X
如何在5分钟内快速安装Homebridge Config UI X 【免费下载链接】homebridge-config-ui-x The Homebridge UI. Monitor, configure and backup Homebridge from a browser. 项目地址: https://gitcode.com/gh_mirrors/ho/homebridge-config-ui-x Homebridge Config UI X …...
OpenClaw+千问3.5-27B学习助手:自动整理笔记与生成思维导图
OpenClaw千问3.5-27B学习助手:自动整理笔记与生成思维导图 1. 为什么需要AI学习助手? 去年准备技术认证考试时,我发现自己陷入了"资料沼泽"——收集了87个PDF、42小时视频课程和无数网页书签,但真正消化吸收的内容不到…...
前端组件库吐槽:别再用那些华而不实的组件了!
前端组件库吐槽:别再用那些华而不实的组件了! 毒舌时刻 前端组件库就像超市里的预制菜——看起来方便,实际吃起来味同嚼蜡。Ant Design、Material UI、Element Plus... 一堆组件库让你挑花了眼,结果你的页面还是丑得像车祸现场。…...
AWS推出新工具简化量子纠错开发流程
谷歌近日将量子计算机实用化时间表提前至2029年,这得益于量子计算机硬件、量子纠错和算法方面的重大改进。2019年,谷歌估计需要2000万个量子比特才能破解RSA加密。到2025年5月,谷歌将这一估计数字下调至100万个。今年2月,澳大利亚…...
Makefile核心概念与高效构建实践指南
1. Makefile基础概念与核心结构Makefile本质上是一种声明式构建脚本,它通过定义目标、依赖和命令三者之间的关系,让构建工具(make)能够智能地决定哪些文件需要重新编译。这种机制在C/C项目中尤为重要,因为源文件之间的…...
千问3.5-9B模型蒸馏:轻量化OpenClaw移动端部署
千问3.5-9B模型蒸馏:轻量化OpenClaw移动端部署 1. 为什么需要端侧轻量化 去年夏天,我在树莓派上尝试部署OpenClaw时遇到了一个尴尬的问题——原版Qwen-14B模型需要至少32GB内存才能流畅运行,而我的树莓派4B仅有8GB。每次启动不到5分钟就会因…...
ESP-01s固件烧录与Arduino编程:从接线玄学到一键下载的避坑指南
1. ESP-01s模块入门:为什么你的接线总是出错? 第一次接触ESP-01s的朋友,十有八九会在烧录固件或上传程序时遇到各种莫名其妙的失败。我见过太多人把模块插上CH340就以为万事大吉,结果在电脑前折腾一整天都搞不定下载。这其实是因为…...
Agent在财务场景有哪些核心应用?深度解析2026企业智能化转型路径
站在2026年的技术节点回望,财务部门早已从传统的“记账中心”转型为企业的“战略决策大脑”。AI Agent(人工智能助手/智能体)的爆发式应用,彻底终结了繁琐的表单时代。与2024年的实验性尝试不同,当下的财务Agent具备了…...
终极TypeScript类型安全指南:LiveTerm接口定义与类型检查最佳实践
终极TypeScript类型安全指南:LiveTerm接口定义与类型检查最佳实践 【免费下载链接】LiveTerm 💻 Build terminal styled websites in minutes! 项目地址: https://gitcode.com/gh_mirrors/li/LiveTerm LiveTerm是一个基于Next.js的终端风格网站构…...
