代码随想录算法训练营第五十八天 | 101.孤岛的总面积、102.沉没孤岛、103.水流问题、104.建造最大岛屿、复习

101.孤岛的总面积

题目链接:https://kamacoder.com/problempage.php?pid=1173
文档讲解:https://programmercarl.com/kamacoder/0101.%E5%AD%A4%E5%B2%9B%E7%9A%84%E6%80%BB%E9%9D%A2%E7…

思路

本题要求找到不靠边的陆地面积,那么我们只要从周边找到陆地然后 通过 dfs或者bfs 将周边靠陆地且相邻的陆地都变成海洋,然后再去重新遍历地图 统计此时还剩下的陆地就可以了。

代码

import java.util.*;class Main {static int[][] grid;static int count = 0;static int[][] dir = {{1, 0}, {0, 1}, {0, -1}, {-1, 0}};public static void main (String[] args) {Scanner in = new Scanner(System.in);int n = in.nextInt(), m = in.nextInt();grid = new int[n][m];for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {grid[i][j] = in.nextInt();}}for (int i = 0; i < n; i++) { // 从第一列和最后一列向中间遍历if (grid[i][0] == 1) bfs(i, 0);if (grid[i][m - 1] == 1) bfs(i, m - 1);}for (int i = 0; i < m; i++) { //从第一行和最后一行向中间遍历if (grid[0][i] == 1) bfs(0, i);if (grid[n - 1][i] == 1) bfs(n - 1, i);}count = 0; // 清空之前记录的陆地数for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {if (grid[i][j] == 1) {bfs(i, j);}} }System.out.println(count);}public static void bfs(int x, int y) {count++;Queue<int[]> queue = new LinkedList<>();queue.offer(new int[]{x, y});grid[x][y] = 0;while (!queue.isEmpty()) {int[] cur = queue.poll();int curX = cur[0], curY = cur[1];for (int i = 0; i < 4; i++) {int nextX = curX + dir[i][0], nextY = curY + dir[i][1];if (nextX < 0 || nextX >= grid.length || nextY < 0 || nextY >= grid[0].length) continue;if (grid[nextX][nextY] == 1) {queue.offer(new int[]{nextX, nextY});grid[nextX][nextY] = 0;count++;}}}}public static void dfs(int x, int y) {grid[x][y] = 0; // 将与边界相连的陆地变为水count++; // 统计陆地数量for (int i = 0; i < 4; i++) {int nextX = x + dir[i][0], nextY = y + dir[i][1];if (nextX < 0 || nextX >= grid.length || nextY < 0 || nextY >= grid[0].length) continue;if (grid[nextX][nextY] == 1) dfs(nextX, nextY);}}
}

这道题在卡码网上提交java的dfs和bfs都会超时,但是思路是和C++一样的。

102.沉没孤岛

题目链接:https://kamacoder.com/problempage.php?pid=1174
文档讲解:https://programmercarl.com/kamacoder/0102.%E6%B2%89%E6%B2%A1%E5%AD%A4%E5%B2%9B.html

思路

第一步:深搜或者广搜将地图周边的 1 (陆地)全部改成 2 (特殊标记)
第二步:将水域中间 1 (陆地)全部改成 水域(0)
第三步:将之前标记的 2 改为 1 (陆地)

代码

import java.util.*;class Main{static int[][] grid;static int[][] dir = {{1, 0}, {0, 1}, {0, -1}, {-1, 0}};public static void main(String[] args) {Scanner in = new Scanner(System.in);int n = in.nextInt(), m = in.nextInt();grid = new int[n][m];for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {grid[i][j] = in.nextInt();}}for (int i = 0; i < n; i++) {if (grid[i][0] == 1) bfs(i, 0);if (grid[i][m - 1] == 1) bfs(i, m - 1);}for (int i = 0; i < m; i++) {if (grid[0][i] == 1) bfs(0, i);if (grid[n - 1][i] == 1) bfs(n - 1, i);}for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {if (grid[i][j] == 1) grid[i][j] = 0;else if (grid[i][j] == 2) grid[i][j] = 1;System.out.print(grid[i][j] + " ");}System.out.println();}}public static void bfs(int x, int y) {Queue<int[]> queue = new LinkedList<>();queue.offer(new int[]{x, y});grid[x][y] = 2;while (!queue.isEmpty()) {int[] cur = queue.poll();int curX = cur[0], curY = cur[1];for (int i = 0; i < 4; i++) {int nextX = curX + dir[i][0], nextY = curY + dir[i][1];if (nextX < 0 || nextX >= grid.length || nextY < 0 || nextY >= grid[0].length) continue;if (grid[nextX][nextY] == 1) {grid[nextX][nextY] = 2;queue.offer(new int[]{nextX, nextY});}}}}public static void dfs(int x, int y) {grid[x][y] = 2;for (int i = 0; i < 4; i++) {int nextX = x + dir[i][0], nextY = y + dir[i][1];if (nextX < 0 || nextX >= grid.length || nextY < 0 || nextY >= grid[0].length) continue;if (grid[nextX][nextY] == 1) dfs(nextX, nextY);}}
}

103.水流问题

题目链接:https://kamacoder.com/problempage.php?pid=1175
文档讲解:https://programmercarl.com/kamacoder/0103.%E6%B0%B4%E6%B5%81%E9%97%AE%E9%A2%98.html

思路

从第一组边界上的节点 逆流而上,将遍历过的节点都标记上。同样从第二组边界的边上节点 逆流而上,将遍历过的节点也标记上。然后两方都标记过的节点就是既可以流第一边界也可以流第二边界的节点。

代码

import java.util.*;class Main {static int[][] grid;static int[][] dir = {{1, 0}, {0, 1}, {0, -1}, {-1, 0}};public static void main (String[] args) {Scanner in = new Scanner(System.in);int n = in.nextInt(), m = in.nextInt();grid = new int[n][m];for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {grid[i][j] = in.nextInt();}}boolean[][] visited1 = new boolean[n][m];boolean[][] visited2 = new boolean[n][m];for (int i = 0; i < n; i++) {bfs(visited1, i, 0); // 最左列,为第一组bfs(visited2, i, m - 1); // 最右列,为第二组}for (int i = 0; i < m; i++) {bfs(visited1, 0, i); // 第一行,为第一组bfs(visited2, n - 1, i); // 第二行,为第二组}for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {if (visited1[i][j] && visited2[i][j]) {System.out.println(i + " " + j);}}}}public static void bfs(boolean[][] visited, int x, int y) {Queue<int[]> queue = new LinkedList<>();queue.offer(new int[]{x, y});visited[x][y] = true;while (!queue.isEmpty()) {int[] cur = queue.poll();int curX = cur[0], curY = cur[1];for (int i = 0; i < 4; i++) {int nextX = curX + dir[i][0], nextY = curY + dir[i][1];if (nextX < 0 || nextX >= grid.length || nextY < 0 || nextY >= grid[0].length) continue;if (!visited[nextX][nextY] && grid[curX][curY] <= grid[nextX][nextY]) {queue.offer(new int[]{nextX, nextY});visited[nextX][nextY] = true;}}}}public static void dfs(boolean[][] visited, int x, int y) {visited[x][y] = true;for (int i = 0; i < 4; i++) {int nextX = x + dir[i][0], nextY = y + dir[i][1];if (nextX < 0 || nextX >= grid.length || nextY < 0 || nextY >= grid[0].length) continue;if (!visited[nextX][nextY] && grid[x][y] <= grid[nextX][nextY]) dfs(visited, nextX, nextY);}}
}

104.建造最大岛屿

题目链接:https://kamacoder.com/problempage.php?pid=1176
文档讲解:https://programmercarl.com/kamacoder/0104.%E5%BB%BA%E9%80%A0%E6%9C%80%E5%A4%A7%E5%B2%9B%E5…

思路

第一步:一次遍历地图,得出各个岛屿的面积,并做编号记录。可以使用map记录,key为岛屿编号,value为岛屿面积
第二步:再遍历地图,遍历0的方格(因为要将0变成1),并统计该1(由0变成的1)周边岛屿面积,将其相邻面积相加在一起,遍历所有 0 之后,就可以得出 选一个0变成1 之后的最大面积。

代码

import java.util.*;
class Main {static int n, m;static int[][] grid;static int[][] markGrid;static boolean[][] visited;static int count;static int[][] dir = {{1, 0}, {0, 1}, {0, -1}, {-1, 0}};static HashMap<Integer, Integer> map = new HashMap<>();public static void main (String[] args) {Scanner in = new Scanner(System.in);n = in.nextInt();m = in.nextInt();grid = new int[n][m];for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {grid[i][j] = in.nextInt();}}markGrid = new int[n][m];visited = new boolean[n][m];// 将岛屿编号,并把对应的面积存入map中int mark = 2;boolean isAllLand = true;for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {if (grid[i][j] == 0) isAllLand = false;if (!visited[i][j] && grid[i][j] == 1) {count = 0;dfs(i, j, mark);map.put(mark, count);mark++;}}}if (isAllLand) System.out.println(n * m);// 如果全是陆地,则直接返回面积n*melse { // 遍历grid值为0的节点,将其四边对应编号的面积相加int res = 0;// 用set来过滤已经添加过的mark值,防止遍历到同一编号的陆地导致重复添加Set<Integer> set = new HashSet<>(); for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {count = 1;set.clear();if (grid[i][j] == 0) {for (int k = 0; k < 4; k++) {int nextX = i + dir[k][0], nextY = j + dir[k][1];if (nextX < 0 || nextX >= n || nextY < 0 || nextY >= m) continue;if (set.contains(grid[nextX][nextY])) continue; // 添加过的岛屿跳过count += map.getOrDefault(grid[nextX][nextY], 0);set.add(grid[nextX][nextY]);}}res = Math.max(res, count);}}System.out.println(res);}}public static void dfs(int x, int y, int mark) {visited[x][y] = true;grid[x][y] = mark;count++;for (int i = 0; i < 4; i++) {int nextX = x + dir[i][0], nextY = y + dir[i][1];if (nextX < 0 || nextX >= n || nextY < 0 || nextY >= m) continue;if (!visited[nextX][nextY] && grid[nextX][nextY] == 1) dfs(nextX, nextY, mark);}}
}

复习二叉树

二叉树理论基础篇
二叉树的递归遍历
二叉树的迭代遍历
二叉树的统一迭代法
二叉树层序遍历

对应题目:

  • 144.二叉树的前序遍历
  • 145.二叉树的后序遍历
  • 94.二叉树的中序遍历

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

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

相关文章

TCP协议深入解析

引言 TCP(Transmission Control Protocol,传输控制协议)是互联网中最重要的协议之一,它为上层应用提供可靠的端到端数据传输服务。TCP协议的设计非常精巧,包含了许多复杂而巧妙的机制。下面让我们一起深入探讨TCP协议的工作原理。 一. TCP连接的建立和断开 连接建立:TCP使用三…

亿发:信息化建设or面子工程?究竟什么才是真正的信息化解决方案

在现代企业的竞争中&#xff0c;信息化建设扮演着越来越重要的角色。信息化技术不仅是企业提升管理效率、优化运营模式的利器&#xff0c;更是企业在市场竞争中脱颖而出的关键。然而&#xff0c;许多企业在推进信息化的过程中&#xff0c;往往容易陷入“面子工程”的误区。那么…

Windows 玩转大模型第二天:流式输出和角色扮演(提示词)(全部代码和详细部署流程)

Windows 玩转大模型第一天&#xff1a;大模型本地部署&#xff0c;调用大模型API可直接工程化应用&#xff08;全部代码和详细部署流程&#xff09;-CSDN博客 流式输出是指模型在生成内容时不是一次性输出全部结果&#xff0c;而是逐步、连续地生成输出。这种方式类似于人类在…

使用笔记之-E语言微信支付支付宝支付源代码

首先下载E语言微信支付&支付宝支付源代码 http://www.htsoft.com.cn/download/E_WeiXin_ZhiFuBao_ZhiFu.rar

【EI会议/稳定检索】2024年农业发展与机械应用国际会议(ADMA 2024)

2024 International Conference on Agricultural Development and Mechanical Applications 2024年农业发展与机械应用国际会议 【会议信息】 会议简称&#xff1a;ADMA 2024 大会时间&#xff1a;点击查看 截稿时间&#xff1a;点击查看 大会地点&#xff1a;中国武汉 会议官…

python作业一

1. #A.方法一 num int(input("请输入要打印的层数:")) for n in range(1, num1):s ""for i in range(1, n1):s f"{i}" " "print(s) #方法二&#xff1a; iint(input("i:")) for i in range(1,i1):s""for j i…

南方健康2024米思会:科普患教赋能医药增长闭环,千亿蓝海市场大爆发!

2024年6月25日-28日&#xff0c;在中国•南太湖举办的2024米思会如约而至&#xff0c;顺利落下帷幕&#xff0c;本次大会以“韧进启新局”为主题&#xff0c;以不懈进取的“韧劲”&#xff0c;立身破局&#xff0c;迎变启新。通过4天3夜的思想碰撞和互动交流&#xff0c;引领行…

Python PyCryptodome库介绍与实例

Python PyCryptodome库介绍与实例 1. 安装2. 基本概念3. 使用场景和示例代码3.1 对称加密 - AES3.2 非对称加密 - RSA3.3 哈希函数 - SHA2563.4 消息认证码 - HMAC 4. 总结 PyCryptodome是一个强大的Python加密库,提供了各种加密算法和工具。本文将介绍PyCryptodome的基本概念和…

【专业指南】移动硬盘坏道下的数据恢复之道

移动硬盘坏道揭秘&#xff1a;数据安全的隐形挑战 在数据日益成为核心资产的今天&#xff0c;移动硬盘作为便携存储的代名词&#xff0c;承载着无数用户的重要信息。然而&#xff0c;随着使用时间的增长和不当操作的影响&#xff0c;移动硬盘可能会遭遇“坏道”这一棘手问题。…

眼动追踪技术 | 眼动的分类和模型

摘要 灵长类动物用于调整中央凹位置的正常眼动&#xff0c;几乎都可以归结为五种基本类型的组合&#xff1a;扫视、平稳追踪、聚散、前庭眼震和生理性眼震(与注视相关的微小运动)。聚散运动用于将双眼聚焦于远处的目标(深度知觉)。其他运动(如适应和聚焦)指的是眼动的非位置变…

密码学原理精解【5】

这里写目录标题 移位密码概述代码 希尔密码( Z 256 Z_{256} Z256​)待加密长度被3整除待加密长度不一定被3整除加解密文件 移位密码 概述 以 z 26 运算为例 , k 为密钥 加密&#xff1a; e k ( x ) ( x k ) m o d 26 解密&#xff1a; d k ( x ) ( x − k ) m o d 26 以z_{…

Linux权限介绍

目录 1.用户切换 2.权限 &#xff08;1&#xff09;权限介绍 &#xff08;2&#xff09;文件类型 &#xff08;3&#xff09;权限组成 &#xff08;4&#xff09;权限修改 &#xff08;5&#xff09;重新认识 &#xff08;6&#xff09;底层操作 &#xff08;一&#x…

Vite 中怎么添加全局 scss 文件

使用 Vite 开发项目&#xff0c;配套周边生态使用起来&#xff0c;开发效率会很高。但也会有一些问题需要解决。 当我们使用 scss 时&#xff0c;希望能够把一些定义变量&#xff0c;定义mixin 的文件全局加载&#xff0c;避免每处用到还要单独引入这些文件。 这就需要一些配…

事件分发机制:demo复现自定义ViewGroup点击事件不起作用

几年前遇到的一个bug&#xff0c;不弄清楚心里就是不舒服&#xff01; 平时应用开发中&#xff0c;经常遇到的UI需求&#xff0c;例如抖音的设置界面&#xff0c;如下图所示&#xff1a; 很容易想到&#xff0c;自定义一个Layout&#xff0c;左边一个图标&#xff0c;中间文…

无痕消除笔怎么用?3款工具教你完美消除

无痕消除笔怎么用&#xff1f;无痕消除笔在图片编辑中扮演着至关重要的角色。它利用先进的图像处理技术&#xff0c;让用户只需简单几步操作&#xff0c;就能轻松抹除图片上任何不想要的细节&#xff0c;无论是明显的瑕疵、多余的文字还是恼人的水印。这一功能不仅提高了编辑效…

华为大咖说 企业应用AI大模型的“道、法、术” -- 法:落地篇 (上)

本文作者&#xff1a;郑岩&#xff08;华为云AI变革首席专家&#xff09;全文约2865字&#xff0c;阅读约需7分钟 在探讨企业如何应用AI大模型的“道、法、术”系列文章的前两篇文章中&#xff0c;我们已经深化了对“AI大模型”的理解&#xff0c;并通过“AI场景12问”洞察了潜…

鸿蒙 HarmonyOS Next 路由 不废话 全干货

一、页面的创建 &#xff08;1&#xff09;直接通过创建一个新的Page的方式创建 &#xff08;2&#xff09;先创建一个 ArkTs File文件&#xff0c;然后在resources/base/profile/main_pages.json中加上页面对应的src路径&#xff0c;下面的Index_3.ets文件是通过创建ArkTs Fi…

【区分vue2和vue3下的element UI Breadcrumb 面包屑组件,分别详细介绍属性,事件,方法如何使用,并举例】

在 Vue 2 中&#xff0c;Element UI 提供了 el-breadcrumb 面包屑组件&#xff0c;而在 Vue 3 中&#xff0c;Element UI 的官方版本并没有直接更新以支持 Vue 3&#xff0c;但有一个类似的库叫做 Element Plus&#xff0c;它是为 Vue 3 设计的。 Vue 2 Element UI 在 Vue 2…

Linux安装达梦

文章目录 前言一、docker安装1.下载镜像2.导入镜像3.生成容器 二、ios安装1.环境准备2.iso安装3.配置实例4.注册服务5.启停服务 总结 前言 公司要求我将数据从oracle迁移到达梦数据库&#xff0c;这个国产数据库以前没用过&#xff0c;所以记录一下这次的安装过程。 一、docke…

【代码随想录算法训练营第五十八天|卡码网101.孤岛的总面积、102.沉没孤岛、103.水流问题、104.建造最大岛屿】

文章目录 101.孤岛的总面积102.沉没孤岛103.水流问题正向逻辑反向逻辑 104.建造最大岛屿 101.孤岛的总面积 可以把最外围的都检查一遍是否有为1的&#xff0c;有的话就把他接壤的全变成海&#xff0c;然后正常算面积。也可以看岛屿是否有靠边的位置&#xff0c;有的话该岛面积…