[A*,启发式搜索] [SCOI2005] 骑士精神
链接:https://ac.nowcoder.com/acm/problem/20247
来源:牛客网
空间限制:C/C++ 262144K,其他语言524288K
64bit IO Format: %lld
题目描述

输入描述:
第一行有一个正整数T(T ≤ 10),表示一共有N组数据
接下来有T个5×5的矩阵,0表示白色骑士,1表示黑色骑 士,*表示空位。两组数据之间没有空行。
输出描述:
对于每组数据都输出一行。如果能在15步以内(包括15步)到达目标状态,则输出步数,否则输出-1。
输出
7
-1
题意:
有一个5*5的棋盘,上面放了24个骑士棋子,和一个空位,每个棋子可以走到和它横坐标相差为1,纵坐标相差为2或者横坐标相差为2,纵坐标相差为1的空位
题目给了一个目标状态,问现在的状态转移到目标状态最少步数是多少,如果最少步数超过15则输出-1
思路:
模拟了第一个样例发现,棋盘中有7个与目标状态不同的骑士,而最少步数为7,也就是说最少步数最少为初始状态中有多少与标准不同的骑士的个数,这样刚好不会浪费格子,
所以枚举最少步数,从空格开始搜索,每次搜索预估代价,当前局面最小移动步数=现在有多少与标准不同的骑士的个数,
步数+预估代价>限制时(到14步时可能会有2个棋子不同但只要一步就能纠正这2个棋子,也就是步数+预估代价==16时是最大可接受范围,所以限制要设为大于等于16的数)或步数大于等于最小可行步数时返回,如果现在局面和标准相同则记录答案(只有步数小于最小可行步数时才会更新答案),
如果搜索越界或现在的操作和上一个操作互逆(如果当前操作和上一个操作互逆却继续搜索那不就返回去了吗)则跳过,
否则交换搜索的棋子和当前棋子并搜索交换棋子的那个位置,且回溯时还原局面
#include<bits/stdc++.h>
using namespace std;
const int amn=,inf=0x3f3f3f3f;
int a[amn][amn],
mp[amn][amn]={
{,,,,},
{,,,,},
{,,,,},
{,,,,},
{,,,,}
}, ///0^1=1,1^1=0,2^1=3,3^1=2,4^1=5,5^1=4...
dt[][]={ ///方向储存时互逆操作相邻,这样就可以通过i^1,判断上一个操作是否和当前操作互逆
{-,-},{,},
{-,-},{,},
{,-},{-,},
{,-},{-,}
};
int ans,lim;
int hst(){ ///预估代价,最小移动步数=现在有多少与标准不同的骑士的个数
int h=;
for(int i=;i<;i++)
for(int j=;j<;j++)
h+=(a[i][j]!=mp[i][j]); ///判断现在有多少与标准不同的骑士
return h;
}
void dfs(int x,int y,int step,int last){
int h=hst();
if(step+h>lim||step>=ans)return; ///步数+预估代价>限制时(到14步时可能会有2个棋子不同但只要一步就能纠正这2个棋子,也就是步数+预估代价==16时是最大可接受范围,所以限制要设为大于等于16的数)或步数大于等于最小可行步数时返回
if(h==){ ///如果现在局面和标准相同则记录答案(只有步数小于最小可行步数时才会更新答案)
ans=step;
return ;
}
for(int i=;i<;i++){
int dx=x+dt[i][],dy=y+dt[i][];
if(dx<||dx>||dy<||dy>||(i^)==last)continue; ///如果搜索越界或现在的操作和上一个操作互逆(如果当前操作和上一个操作互逆却继续搜索那不就返回去了吗)则跳过
swap(a[dx][dy],a[x][y]); ///交换
dfs(dx,dy,step+,i);
swap(a[dx][dy],a[x][y]); ///回溯时还原局面
}
}
int main(){
int T,stx,sty;
char in;
scanf("%d",&T);
getchar();
while(T--){
for(int i=;i<;i++){
for(int j=;j<;j++){
scanf("%c",&in);
if(in=='')
a[i][j]=;
else if(in=='')
a[i][j]=;
else
a[i][j]=,stx=i,sty=j;
}
getchar();
}
ans=inf;
int h=hst();
for(int i=h;i<=;i++){ ///枚举限制,最小限制从现在有多少与标准不同的骑士的个数开始,到一个大于等于16的数(太大了会超时),
到14步时可能会有2个棋子不同但只要一步就能纠正这2个棋子,也就是步数+预估代价==16时是最大可接受范围,所以限制要设为大于等于16的数
lim=i;
dfs(stx,sty,,inf);
}
printf("%d\n",ans>?-:ans);
}
}
/**
有一个5*5的棋盘,上面放了24个骑士棋子,和一个空位,每个棋子可以走到和它横坐标相差为1,纵坐标相差为2或者横坐标相差为2,纵坐标相差为1的空位
题目给了一个目标状态,问现在的状态转移到目标状态最少步数是多少,如果最少步数超过15则输出-1
模拟了第一个样例发现,棋盘中有7个与目标状态不同的骑士,而最少步数为7,也就是说最少步数最少为初始状态中有多少与标准不同的骑士的个数,这样刚好不会浪费格子,
所以枚举最少步数,从空格开始搜索,每次搜索预估代价,当前局面最小移动步数=现在有多少与标准不同的骑士的个数,
步数-1+预估代价>限制时(到14步时可能会有2个棋子不同但只要一步就能纠正这2个棋子,也就是步数+预估代价==16时是最大可接受范围,所以限制要设为大于等于16的数)或步数大于等于最小可行步数时返回,如果现在局面和标准相同则记录答案(只有步数小于最小可行步数时才会更新答案),
如果搜索越界或现在的操作和上一个操作互逆(如果当前操作和上一个操作互逆却继续搜索那不就返回去了吗)则跳过,
否则交换搜索的棋子和当前棋子并搜索交换棋子的那个位置,且回溯时还原局面
**/
[A*,启发式搜索] [SCOI2005] 骑士精神的更多相关文章
- BZOJ 1085 [SCOI2005]骑士精神 【A*启发式搜索】
1085: [SCOI2005]骑士精神 Time Limit: 10 Sec Memory Limit: 162 MB Submit: 2838 Solved: 1663 [Submit][St ...
- BZOJ1085: [SCOI2005]骑士精神 [迭代加深搜索 IDA*]
1085: [SCOI2005]骑士精神 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 1800 Solved: 984[Submit][Statu ...
- 【bzoj1085】[SCOI2005]骑士精神
1085: [SCOI2005]骑士精神 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 1757 Solved: 961[Submit][Statu ...
- BZOJ 1085: [SCOI2005]骑士精神( IDDFS + A* )
一开始写了个 BFS 然后就 T 了... 这道题是迭代加深搜索 + A* -------------------------------------------------------------- ...
- BZOJ_1085_[SCOI2005]骑士精神_IDDFS
BZOJ_1085_[SCOI2005]骑士精神_DFS Description 在一个5×5的棋盘上有12个白色的骑士和12个黑色的骑士, 且有一个空位.在任何时候一个骑士都能按照骑 士的走法(它可 ...
- [luogu P2324] [SCOI2005]骑士精神
[luogu P2324] [SCOI2005]骑士精神 题目描述 输入输出格式 输入格式: 第一行有一个正整数T(T<=10),表示一共有N组数据.接下来有T个5×5的矩阵,0表示白色骑士,1 ...
- 【洛谷】2324:[SCOI2005]骑士精神【IDA*】
P2324 [SCOI2005]骑士精神 题目描述 输入输出格式 输入格式: 第一行有一个正整数T(T<=10),表示一共有N组数据.接下来有T个5×5的矩阵,0表示白色骑士,1表示黑色骑士,* ...
- BZOJ1085 SCOI2005 骑士精神【IDA* 启发式迭代加深】
BZOJ1085 SCOI2005 骑士精神 Description 在一个5×5的棋盘上有12个白色的骑士和12个黑色的骑士, 且有一个空位.在任何时候一个骑士都能按照骑士的走法(它可以走到和它横坐 ...
- 洛谷 P2324 [SCOI2005]骑士精神 解题报告
P2324 [SCOI2005]骑士精神 题目描述 输入输出格式 输入格式: 第一行有一个正整数T(T<=10),表示一共有N组数据.接下来有T个5×5的矩阵,0表示白色骑士,1表示黑色骑士,* ...
随机推荐
- HBase源码系列之HFile
本文讨论0.98版本的hbase里v2版本.其实对于HFile能有一个大体的较深入理解是在我去查看"到底是不是一条记录不能垮block"的时候突然意识到的. 首先说一个对HFile ...
- VI.应用-Trajectory Data Mining
$textbf{Trajectory Data Mining: An Overview}$ 很好的一篇概述,清晰明了地阐述了其框架,涉及内容又十分宽泛.值得细读. 未完成,需要补充. $textbf{ ...
- 量化投资学习笔记29——《Python机器学习应用》课程笔记03
聚类的实际应用,图像分割. 利用图像的特征将图像分割为多个不相重叠的区域. 常用的方法有阈值分割,边缘分割,直方图法,特定理论(基于聚类,小波分析等). 实例:利用k-means聚类算法对图像像素点颜 ...
- BeetleX之XRPC远程委托调用
BeetleX.XRPC是基于接口的远程通讯组件,它不紧可以把接口提供客户端调用,同样也支持服务端创建客户端的接口实例并主动调用客户端的方法.接口有着非常的规范性和约束性,但前提你是必须制定相应的接口 ...
- 东南大学RM装甲板识别算法详解
rm中,装甲板的识别在比赛中可谓是最基础的算法.而在各个开源框架中,该算法也可以说最为成熟.出于学习目的,之后将对比多个高校或网络代码(),尝试学习各个rm装甲板识别算法的优点和流程. 这次先是东南大 ...
- JavaWeb中登录验证码生成
1.页面代码 <html> <head> <title>Title</title> <script type="text/javascr ...
- C#版免费离线人脸识别——虹软ArcSoft V3.0
[温馨提示] 本文共678字(不含代码),8张图.预计阅读时间需要6分钟. 1. 前言 人脸识别&比对发展到今天,已经是一个非常成熟的技术了,而且应用在生活的方方面面,比如手机.车站.天网等. ...
- Python 三程三器的那些事
装饰器 1.什么是装饰器 装饰器本质是函数,用来给其他函数添加新的功能 特点:不修改调用方式.不修改源代码 2.装饰器的作用 装饰器作用:本质是函数(装饰其他函数)就是为其他函数添加其他功能 装饰器必 ...
- 峰哥说技术:09-Spring Boot整合JSP视图
Spring Boot深度课程系列 峰哥说技术—2020庚子年重磅推出.战胜病毒.我们在行动 09 峰哥说技术:Spring Boot整合JSP视图 一般来说我们很少推荐大家在Spring boot ...
- CVE-2020-1947 Sharding-UI的反序列化复现及分析
CVE-2020-1947 复现及分析 0x01 影响 Apache ShardingSphere < =4.0.0 0x02 环境搭建 incubator-shardingsphere 的ui ...