USACO Training3.3亚瑟王的宫殿【搜索】By cellur925
因为太蒟了,所以参考了dalao@zbtrs == 对此表示感谢并侵删。
看起来我们就知道这是搜索题。
最后的情况分两种:有骑士背国王/国王自食其力走到集合点。
首先,我们不知道大家最后集合在哪里,所以可以枚举一下这个点。
其次,我们不知道是哪个骑士背,所以再枚举一下。
再次,我们不知道在哪里接国王,所以再枚举一下这个点。
这是思路的大体框架。然后在更新答案时,我们需要求出在棋盘上一个点到另一点的最短距离。然后因为我们可以等效的认为这是一个无向无环图,所以直接用bfs顺便跑出最短距离就行了==。
细节:赋初值。dis数组和ans都要赋成正无穷。因为我们在寻求一个最小值。
优化:最优性剪枝(代码中)
Code
/*
ID:cellur_2
TASK:camelot
LANG:C++
*/
#include<cstdio>
#include<algorithm>
#include<queue>
#include<cstring> using namespace std;
const int inf=0x3f3f3f; int n,m,cnt,ans=inf;
char ch[];
bool vis[][];
int dx[]={,-,-,,,,,-,-};
int dy[]={,,,,,-,-,-,-};
int dis[][][][];
int kingx,kingy;
struct point{
int x,y;
}knight[]; bool valid(int x,int y)
{
if(x>=&&x<=n&&y>=&y<=m) return ;
return ;
} void bfs(int x,int y)
{
queue<pair<int,int> >q;
q.push(make_pair(x,y));
memset(vis,,sizeof(vis));
vis[x][y]=;
dis[x][y][x][y]=;
while(!q.empty())
{
int xx=q.front().first;
int yy=q.front().second;
q.pop();
int step=dis[x][y][xx][yy];
for(int i=;i<=;i++)
{
int rx=xx+dx[i];
int ry=yy+dy[i];
if(valid(rx,ry)&&!vis[rx][ry])
{
dis[x][y][rx][ry]=step+;
q.push(make_pair(rx,ry));
vis[rx][ry]=;
}
}
}
} int main()
{
freopen("camelot.in","r",stdin);
freopen("camelot.out","w",stdout);
scanf("%d%d",&n,&m);
scanf("%s",ch+);kingy=(int)ch[]-'A'+;
scanf("%d",&kingx);kingx=n-kingx+;
while(scanf("%s",ch+)!=EOF)
{
knight[++cnt].y=(int)ch[]-'A'+;
scanf("%d",&knight[cnt].x);
knight[cnt].x=n-knight[cnt].x+;
}
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
for(int a=;a<=n;a++)
for(int b=;b<=m;b++)
dis[i][j][a][b]=inf;
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
bfs(i,j);
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
{
int tmp=;
for(int k=;k<=cnt;k++)
tmp+=dis[knight[k].x][knight[k].y][i][j];
ans=min(ans,tmp+max(abs(kingx-i),abs(kingy-j)));
//先考虑国王不被帮助运送的情况
for(int k=;k<=cnt;k++)
{//需要重开变量,不能偷懒用tmp直接减,否则会一直减
int tmpp=tmp-dis[knight[k].x][knight[k].y][i][j];
if(tmp>=ans) continue;//最优性剪枝
for(int l=;l<=n;l++)
for(int r=;r<=m;r++)
ans=min(ans,tmpp+dis[knight[k].x][knight[k].y][l][r]+dis[l][r][i][j]+max(abs(kingx-l),abs(kingy-r)));
}
}
printf("%d\n",ans);
return ;
}
USACO Training3.3亚瑟王的宫殿【搜索】By cellur925的更多相关文章
- 洛谷P1930 亚瑟王的宫殿 Camelot
P1930 亚瑟王的宫殿 Camelot 19通过 53提交 题目提供者JOHNKRAM 标签USACO 难度提高+/省选- 提交 讨论 题解 最新讨论 暂时没有讨论 题目描述 很久以前,亚瑟王和 ...
- 洛谷 P1930 亚瑟王的宫殿 Camelot
传送门 题目大意:棋盘有骑士有王,让所有点跳到一个点,求所有棋子跳的步数和,和最小. 题解:bfs+枚举 王的人生: 1):自己走到聚集点 2):某个骑士来到王这里,两个棋子一起到聚集点 3):王走几 ...
- BZOJ 4008 【HNOI2015】 亚瑟王
题目链接:亚瑟王 这道题好神啊TAT--果然我的dp还是太弱了-- 一开始想了半天的直接dp求期望,结果最后WA的不知所云-- 最后去翻了题解,然后发现先算概率,再求期望--新姿势\(get\). 我 ...
- Bzoj4008 [HNOI2015]亚瑟王
Time Limit: 20 Sec Memory Limit: 512 MBSec Special Judge Submit: 1009 Solved: 605[Submit][Status] ...
- 【BZOJ4008】[HNOI2015]亚瑟王 期望
[BZOJ4008][HNOI2015]亚瑟王 Description 小 K 不慎被 LL 邪教洗脑了,洗脑程度深到他甚至想要从亚瑟王邪教中脱坑. 他决定,在脱坑之前,最后再来打一盘亚瑟王.既然是最 ...
- 【BZOJ-4008】亚瑟王 概率与期望 + DP
4008: [HNOI2015]亚瑟王 Time Limit: 20 Sec Memory Limit: 512 MBSec Special JudgeSubmit: 832 Solved: 5 ...
- BZOJ 4008 亚瑟王
Description 小K不慎被LL邪教洗脑了,洗脑程度深到他甚至想要从亚瑟王邪教中脱坑. 他决定,在脱坑之前,最后再来打一盘亚瑟王.既然是最后一战,就一定要打得漂亮.众所周知,亚瑟王是一个看脸的游 ...
- BZOJ 4008: [HNOI2015]亚瑟王( dp )
dp(i, j)表示考虑了前i张牌, 然后还有j轮的概率. 考虑第i+1张牌: 发动的概率 : p = dp(i, j) * (1 - (1-p[i+1])^j) 没发动的概率 : dp(i, j) ...
- [BZOJ4008]亚瑟王
Description 小 K 不慎被 LL 邪教洗脑了,洗脑程度深到他甚至想要从亚瑟王邪教中脱坑. 他决定,在脱坑之前,最后再来打一盘亚瑟王.既然是最后一战,就一定要打得漂 亮.众所周知,亚瑟王是一 ...
随机推荐
- js 监控浏览器关闭(完美兼容chrome & ie & fire fox)
var UnloadConfirm = {}; UnloadConfirm.MSG_UNLOAD = "数据尚未保存,离开后可能会导致数据丢失\n\n您确定要离开吗?"; Unlo ...
- Computer form factor
http://en.wikipedia.org/wiki/Motherboard_form_factor Computer form factor From Wikipedia, the free e ...
- [LeetCode] 038. Count and Say (Easy) (C++/Python)
索引:[LeetCode] Leetcode 题解索引 (C++/Java/Python/Sql) Github: https://github.com/illuz/leetcode 038. Cou ...
- SQL面试练习(MySql)
创建测试数据库: /*如果已经存在此数据库,先删除*/ drop database if exists sqltest ; /*创建并设置编码为UTF-8*/ create database sqlt ...
- Class.forName("java.lang.String")的作用?
返回字节码: 返回的方式有2种: 第一种是这个类的字节码已经加载到内存里面来了,现在想要取到它的字节码,我直接找到那份字节码把他返回: 第二种是我去得到这个类的字节码,结果在虚拟机里面还没有这个类的字 ...
- hadoop-client
<!-- https://mvnrepository.com/artifact/org.apache.hadoop/hadoop-common --> <dependency> ...
- Hibernate commit() 和flush() 的区别
<<精通Hibernate java对象持久化技术详解>> ,flush()方法进行清理缓存的操作,执行一系列的SQL语句,但不会提交事务;commit()方法会先调用flus ...
- mysql字符串的常用函数(截取和拼接)
#截取字符串(先正序取2个,再倒序取1个)SELECT SUBSTRING_INDEX(SUBSTRING_INDEX('aaa-gg-cc-dd','-',2),'-',-1) #获取子表某个字段的 ...
- eclipse软件启动弹窗端口问题解决
如果启动eclipse,弹出一个窗口,上面显示,8080 .8009.……等的提示,说明端口有冲突, 解决办法如下: 1.打开cmd 2.输入 netstat -ano|findstr 8080 ...
- [置顶] SQL Server 2005 双机热备的实现
[置顶] SQL Server 2005 双机热备的实现 分类: SQLSERVER2011-08-24 21:25 901人阅读 评论(0) 收藏 举报 sql servermicrosoftsql ...