深度优先搜索DFS与记忆化搜索

深度优先搜索(DFS)

求连通块 👉HDOJ-1241 Oil Deposits

【题目】石油勘探公司把油田分成许多的大格,每个大格又分为许多小格,然后分析各个小格是否有石油矿藏。有矿藏的小格(用@表示)称为容器. 如果2个容器相连(横、竖、斜), 则它们是同一矿区的不同部分。输入各大格的矿藏分布(无矿藏用*表示),输出其中有多少个不同的矿区。

#include<iostream>
using namespace std;
char g[105][105]={0};
int m,n;
int dir[8][2]={{-1,-1},{-1,0},{-1,1},{0,-1},{0,1},{1,-1},{1,0},{1,1}};
void dfs(int x,int y){if(x<0||x==m||y<0||y==n||g[x][y]=='*') return;//越界或走过,则返回g[x][y]='*';//标记走过for(int k=0;k<8;k++)//查找下一级可用点dfs(x+dir[k][0],y+dir[k][1]);
}
int main(){	while(cin>>m>>n&&m){//m行n列int i,j;for(i=0;i<m;i++)//建议从0开始,便于整行输入cin>>g[i];int num=0;for(i=0;i<m;i++)for(j=0;j<n;j++)if(g[i][j]=='@')//仅在第一级递归计数,故分离{num++;dfs(i,j);}cout<<num<<endl;}return 0;
}

👉HDOJ-1031 N皇后问题

【题目】在N×N的方格棋盘放置了N个皇后,使得它们不相互攻击(即任意2个皇后不允许处在同一排,同一列,也不允许处在与棋盘边框成45角的斜线上。输入给定的N(N≤10),输出有多少种合法的放置方法。

【思路】在N×N棋盘中摆N个皇后,意味着每行有一个皇后,每列有一个皇后,每条主对角线有一个皇后,每条副对角线有一个皇后;换言之,每个皇后控制着一行、一列。一条主对角线、一条副对角线。因此,以每行对应一次循环,用a,b,c三个数组存储各主对角线、副对角线、列的占用情况。点(x,y)位于第x行,第y列,第y-x+n条主对角线(1-n<=y-x<=n-1,处理使数组从1开始),第x+y条副对角线(2<=x+y<=2n)。

#include<iostream>
#include<cstring>
using namespace std;
int n,so;
bool a[25],b[15],c[25];//a代表主对角线,b代表列,c代表副对角线
void dfs(int i){if(i>n) {so++;return;}for(int j=1;j<=n;j++){//每列if(a[j-i+n]||b[j]||c[i+j]) continue;//不可用,则跳过a[j-i+n]=true;b[j]=true;c[i+j]=true;//标记控制区域dfs(i+1);//查找下一行可用点a[j-i+n]=false;b[j]=false;c[i+j]=false;//取消标记}
}
int main(){int ans[15]={0};for(n=1;n<=10;n++){memset(a,false,sizeof(a));memset(b,false,sizeof(b));memset(c,false,sizeof(c));	so=0;dfs(1);ans[n]=so;}while(cin>>n&&n)cout<<ans[n]<<endl;return 0;
}

👉HDOJ-1426 Sudoku Killer

【题目】输入一批不完整的数独地图(未知数值用?表示),输出它们的解。(对于每组测试数据保证它有且只有一个解)

【思路】
仔细分析,发现与上一题有类似之处:小格中的每一个数字x,都可以看做是所在行、列、九宫格的数字x的控制数字——这个数字控制着所在行、列、九宫格,在其控制区域内不能出现另一个x。用结构体存储空格的位置,i(0~8)代表小格行标,j(0~8)代表小格列标,则i/3代表九宫格行标,j/3代表九宫格列标。以每个空格对应一层递归,用a,b,c三个数组存储各行、列、九宫格的可用性,数组最后一维代表9个可能的数字,其他维度代表序号。
由题意,每个空格的值不全为9。当从最后一个空格(已填写)出发进行下一层递归时,触发条件空格溢出,记录填写完成,函数返回到倒数第二个空格的下一次循环。填写完成条件满足,循环变量的上一个值填写到真正的数独空格中,函数再返回到倒数第三个空格……对于值为9的情况,在循环之外另行处理。
用两层循环读入数独地图存到字符数组中,读入的字符若是数字,标记控制区域;若是空格,记录其位置坐标。

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
char map[9][9];
struct space{int i;int j;}s[81];
bool a[9][12],b[9][12],c[3][3][12];//a代表行,b代表列,c代表九宫格
int sn,snm;//sn=Space Number空格编号,snm=空格编号最大值
int done;//done为1代表所有空格填写完成
void dfs(int sn){if(sn>snm) {done=1;return;}int v;for(v=1;v<=9;v++){//每个可能值if(done==1) {map[s[sn].i][s[sn].j]='0'+v-1;break;}if(a[s[sn].i][v]||b[s[sn].j][v]||c[s[sn].i/3][s[sn].j/3][v]) continue;//不可用,则跳过a[s[sn].i][v]=true;b[s[sn].j][v]=true;c[s[sn].i/3][s[sn].j/3][v]=true;//标记控制区域dfs(sn+1);//填写下一个空格a[s[sn].i][v]=false;b[s[sn].j][v]=false;c[s[sn].i/3][s[sn].j/3][v]=false;//取消标记}if(v==10&&done==1) map[s[sn].i][s[sn].j]='0'+v-1;
}
int main(){char ch;int f=1;do{int i,j;memset(a,false,sizeof(a));memset(b,false,sizeof(b));memset(c,false,sizeof(c));done=0;sn=0;for(i=0;i<9;i++){for(j=0;j<9;j++){cin>>ch;if(ch!='?') {a[i][ch-'0']=true;b[j][ch-'0']=true;c[i/3][j/3][ch-'0']=true;}else {s[sn].i=i;s[sn].j=j;sn++;}map[i][j]=ch;}}snm=sn-1;dfs(0);if(f==0) cout<<endl; else f=0;//第二组数据开始,输出前加一空行for(i=0;i<9;i++){for(j=0;j<8;j++)cout<<map[i][j]<<" ";cout<<map[i][j]<<endl;			}	}while(scanf("%c",&ch)!=EOF);return 0;
}

【总结】1031 之前以单个方格作为区域可用性的存储单元,这样一个方格可能被多个皇后控制,故不能用bool标记,而是放上一个皇后将其占用区域与控制区域值加1,取消标记时将皇后将其占用区域与控制区域值减1。在处理射线扩展时,方向数组与越界判断繁复,放弃。参考他人之后,发现利用棋盘长宽等长的条件可以简化问题。

记忆化搜索

【题目】
○题目描述
在一个数阵中,求出最长的严格下降路径的长度(只能向相邻的上下左右走);
如在下面这个数阵中最长的路径为:25->24->23…->1(长度为25)
1 2 3 4 5
16 17 18 19 6
15 24 25 20 7
14 23 22 21 8
13 12 11 10 9
○输入
第一行包含测试用例数T。每个测试用例第1行是名称(字符串)、行数r和列数c。之后是r行,每行有c个数。N和r和c不大于100;
○输出
对于每个测试用例,打印一行,其中包含区域名称、冒号、空格和最长长度。
○样例输入
1
scj 10 5
56 14 51 58 88
26 94 24 39 41
24 16 8 51 51
76 72 77 43 10
38 50 59 84 81
5 23 37 71 77
96 10 93 53 82
94 15 96 69 9
74 0 62 38 96
37 54 55 82 38
○样例输出
scj: 7

【思路】
dp[i][j]存储从a[i][j]开始的最长路径长度,则dp[i][j]=1+max(dp[x][y])
(点(x,y)与(i,j)相邻且不越界,且满足a[i][j]>a[x][y],若不存在这样的点,max值为0)
递推需要遵循线性顺序,而本题涉及路径,故使用记忆化搜索。记忆化搜索涉及递归,原因是搜索过程中调用的结果可能尚未生成,需要针对调用对象展开进一层搜索。
用一个函数来生成dp[i][j]的值,函数执行过程中会更新从(i,j)出发的所有路径上的点的dp值,但路径不一定包含所有点。在遍历所有点之后, a n s = max ⁡ 1 ≤ i ≤ r , 1 ≤ j ≤ c d p [ i ] [ j ] ans=\max_{1≤i≤r,1≤j≤c} dp[i][j] ans=1ir,1jcmaxdp[i][j]

#include<queue>
#include<algorithm>
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int r, c;
int a[105][105];
int dp[105][105];
int search(int n, int m){int temp = a[n][m];if(n - 1 > 0 && a[n-1][m] < temp) {if(dp[n-1][m] != 0) dp[n][m] = max(dp[n][m], dp[n-1][m] + 1);else dp[n][m] = max(dp[n][m], search(n-1, m) + 1);}if(n + 1 <= r && a[n+1][m] < temp) {if(dp[n+1][m] != 0) dp[n][m] = max(dp[n][m], dp[n+1][m] + 1);else dp[n][m] = max(dp[n][m], search(n+1, m) + 1);}if(m - 1 > 0 && a[n][m-1] < temp) {if(dp[n][m-1] != 0) dp[n][m] = max(dp[n][m], dp[n][m-1] + 1);else dp[n][m] = max(dp[n][m], search(n, m-1) + 1);}if(m + 1 <= c && a[n][m+1] < temp) {if(dp[n][m+1] != 0) dp[n][m] = max(dp[n][m], dp[n][m+1] + 1);else dp[n][m] = max(dp[n][m], search(n, m+1) + 1);}return dp[n][m];
}int main() {int t;scanf("%d", &t);while(t--){memset(dp, 0, sizeof(dp));char ch[105];scanf("%s", ch);scanf("%d %d", &r, &c);for(int i = 1; i <= r; i++) for(int j = 1; j <= c; j++) scanf("%d", &a[i][j]);int maxmum = 0;for(int i = 1; i <= r; i++) for(int j = 1; j <= c; j++)maxmum = max(maxmum, search(i, j));printf("%s: ", ch);printf("%d\n", maxmum + 1);}return 0;
}

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

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

相关文章

基于ssm实验室课程管理系统源码和论文

idea 数据库mysql5.7 数据库链接工具&#xff1a;navcat,小海豚等 环境&#xff1a; jdk8 tomcat8.5 摘 要 随着科学实验规模的不断扩大&#xff0c;实验室课程数量的急剧增加&#xff0c;有关实验室课程的各种信息量也在不断成倍增长。面对庞大的信息量&#xff0c;就需要有…

HBase 使用JDK21

HBase 使用JDK21 启动zookeeper和hadoop 创建软件目录 mkdir -p /opt/soft cd /opt/soft下载软件 wget https://dlcdn.apache.org/hbase/2.5.6/hbase-2.5.6-hadoop3-bin.tar.gz解压 hbase tar -zxvf hbase-2.5.6-hadoop3-bin.tar.gz修改 hbase 目录名称 mv hbase-2.5.6-had…

一则广告,一个故事,这就我选择学习计算机专业的两个原因

还记得当初自己为什么选择计算机&#xff1f; 现在回想起来&#xff0c;当初驱使自己选择学习计算机专业的原因&#xff0c;一共有两个&#xff1a; 一、一则长城电脑的广告。 上个世纪80年代&#xff0c;我还在读小学&#xff0c;当时在中央电视台上经常播放着的长城电脑的一则…

Abaqus基础教程--胶合失效仿真

胶合是电子行业中常见的连接方式&#xff0c;abaqus中常用cohesive单元或者cohesive接触两种方法进行胶合失效仿真&#xff0c;这两种方式操作方法有所差别&#xff0c;但结果一般大同小异。 本例模型比较简单&#xff0c;建模过程从略&#xff0c;使用静态分析&#xff0c;使…

【GAMES101】三维变换

games101的第四节课讲了三维变换和观察变换&#xff0c;我们这里先记录一下三维变换的知识&#xff0c;后面再讲观察变换 齐次坐标下的三维变换 类似于解决之前二维变换平移的问题&#xff0c;三维变换下用齐次坐标通过增加一个维度来表示&#xff0c;第四个维度为1表示这是个…

Spring-Security取消验证-Get请求接口正常,Post请求报错403

现象&#xff1a;springcloud项目夹带security相关的包后启动提示如下&#xff1a; Using generated security password: f67f9afa-xxxxxxxxxxx-a85e-88175f5a7c8aThis generated password is for development use only. Your security configuration must be updated before …

无敌是多么的寂寞!一本书讲透Java多线程!吊打多线程从原理到实践!

摘要 互联网的每一个角落&#xff0c;无论是大型电商平台的秒杀活动&#xff0c;社交平台的实时消息推送&#xff0c;还是在线视频平台的流量洪峰&#xff0c;背后都离不开多线程技术的支持。在数字化转型的过程中&#xff0c;高并发、高性能是衡量系统性能的核心指标&#xff…

vue2+electron桌面端一体机应用

vue2+electron项目 前言:公司有一个项目需要用Vue转成exe,首先我使用vue-cli脚手架搭建vue2项目,然后安装electron 安装electron 这一步骤可以省略,安装electron-builder时会自动安装electron npm i electron 安装electron-builder vue add electron-builder 项目中多出…

(NeRF学习)3D Gaussian Splatting Instant-NGP

学习参考&#xff1a; 3D Gaussian Splatting入门指南【五分钟学会渲染自己的NeRF模型&#xff0c;有手就行&#xff01;】 三维重建instant-ngp环境部署与colmap、ffmpeg的脚本参数使用 一、3D Gaussian Splatting &#xff08;一&#xff09;3D Gaussian Splatting环境配置…

JVM 类的加载器的基本特征和作用

Java全能学习面试指南&#xff1a;https://javaxiaobear.cn 1、作用 类加载器是 JVM 执行类加载机制的前提 ClassLoader的作用&#xff1a; ClassLoader是Java的核心组件&#xff0c;所有的Class都是由ClassLoader进行加载的&#xff0c;ClassLoader负责通过各种方式将Class信…

【跨境营商】创新科技助力数码转型 增强大湾区企业核心竞争力

粤港澳大湾区作为国家的重点发展区域&#xff0c;坐拥丰富的资源及商机&#xff0c;企业积极推行数码化&#xff0c;务求在大湾区抢占先机。香港电讯商业客户业务董事总经理吴家隆表示&#xff0c;近年企业锐意加快数码化步伐&#xff0c;香港电讯以创新科技融入的数码方案&…

UE学习C++(1)创建actor

创建新C类 在 虚幻编辑器 中&#xff0c;点击 文件&#xff08;File&#xff09; 下拉菜单&#xff0c;然后选择 新建C类...&#xff08;New C Class...&#xff09; 命令&#xff1a; 此时将显示 选择父类&#xff08;Choose Parent Class&#xff09; 菜单。可以选择要扩展的…

Linux Component概述和高通V4l2驱动模型

1 Linux为什么要引入Component框架&#xff1f; 为了让subsystem按照一定顺序初始化设备才提出来的。 subsystem中由很多设备模块&#xff0c;内核加载这些模块的时间不确定。子系统内有些模块是需要依赖其它模块先初始化才能进行自己初始化工作(例如v4l2 subdev和v4l2 video …

代码随想录算法训练营第四十二天| 416 分割等和子集

目录 416 分割等和子集 416 分割等和子集 class Solution { public:const int N 210;bool canPartition(vector<int>& nums) {vector<int>f(N);int sum 0;for(auto num : nums)sum num;if(sum % 2 1)return false;//如果int target sum / 2;for(int i …

电商类直播介绍

电商直播是一种购物方式&#xff0c;通过直播技术向消费者展示商品&#xff0c;并引导其进行购买。在法律上&#xff0c;电商直播属于商业广告活动&#xff0c;主播需要根据具体行为承担“广告代言人"“广告发布者"或“广告主"的责任。 电商直播的特点在于其更…

月薪6W!美团、网易等大厂急招HarmonyOS开发!

近期&#xff0c;多家互联网公司发布了多个和鸿蒙系统有关的岗位。 不仅如此&#xff0c;还与Windows等主流老牌操作系统并列&#xff0c;并且排在首位介绍。 此外&#xff0c;今日头条招聘Android开发工程师也提及岗位需要“负责今日头条 Android、鸿蒙系统等新技术方向调研…

Http协议与Tomcat

HTTP协议 HTTP协议&#xff08;HyperText Transfer Protocol&#xff09;即超文本传输协议 &#xff0c;是TCP/IC网络体系结构应用层的一个客户端-服务端协议&#xff0c;是所有客户端&#xff0c;服务端数据传输的基石&#xff08;数据传输规则&#xff09; 特点 ⭐基于TCP协…

class059 建图、链式前向星、拓扑排序【算法】

class059 建图、链式前向星、拓扑排序【算法】 code1 建图 package class059;import java.util.ArrayList; import java.util.Arrays;public class Code01_CreateGraph {// 点的最大数量public static int MAXN 11;// 边的最大数量// 只有链式前向星方式建图需要这个数量// 注…

基于AT89C51单片机的秒表设计

1&#xff0e;设计任务 利用单片机AT89C51设计秒表&#xff0c;设计计时长度为9:59:59&#xff0c;超过该长度&#xff0c;报警。创新&#xff1a;设置重启&#xff1b;暂停&#xff1b;清零等按钮。最后10s时播放音乐提示。 本设计是采用AT89C51单片机为中心&#xff0c;利用其…

zabbix的自动发现和注册、proxy代理和SNMP监控

目录 一、zabbix自动发现与自动注册机制&#xff1a; 1、概念 2、zabbix 自动发现与自动注册的部署 二、zabbix的proxy代理功能&#xff1a; 1、工作流程 2、安装部署 三、zabbix-snmp 监控 1、概念 2、安装部署 四、总结&#xff1a; 一、zabbix自动发现与自动注册…