【题目描述】 原题目链接地址:
  有一个m × m的棋盘,棋盘上每一个格子可能是红色、黄色或没有任何颜色的。你现在要从棋盘的最左上角走到棋盘的最右下角。
任何一个时刻,你所站在的位置必须是有颜色的(不能是无色的),你只能向上、下、左、右四个方向前进。当你从一个格子走向另一个格子时,如果两个格子的颜色相同,那你不需要花费金币;如果不同,则你需要花费 1 个金币。
  另外,你可以花费 2 个金币施展魔法让下一个无色格子暂时变为你指定的颜色。但这个魔法不能连续使用,而且这个魔法的持续时间很短,也就是说,如果你使用了这个魔法,走到了这个暂时有颜色的格子上,你就不能继续使用魔法;只有当你离开这个位置,走到一个本来就有颜色的格子上的时候,你才能继续使用这个魔法,而当你离开了这个位置(施展魔法使得变为有颜色的格子)时,这个格子恢复为无色。
  现在你要从棋盘的最左上角,走到棋盘的最右下角,求花费的最少金币是多少?
【输入格式】
  数据的第一行包含两个正整数 m,n,以一个空格分开,分别代表棋盘的大小,棋盘上 有颜色的格子的数量。
  接下来的 n 行,每行三个正整数 x,y,c,分别表示坐标为(x,y)的格子有颜色 c。其中 c=1 代表黄色,c=0 代表红色。 相邻两个数之间用一个空格隔开。 棋盘左上角的坐标为(1, 1),右下角的坐标为(m, m)。
  棋盘上其余的格子都是无色。保证棋盘的左上角,也就是(1,1)一定是有颜色的。
【输出格式】
  输出一行,一个整数,表示花费的金币的最小值,如果无法到达,输出-1。
【样例输入1】
5 7
1 1 0
1 2 0
2 2 1
3 3 1
3 4 0
4 4 1
5 5 0
【样例输出1】
8
 
图片省略~~
-------------------------------------------------------------------------------

分析:记忆化搜索, 用DP[i][j]表示走到(i,j)时的最小代价,如果当前深搜到的代价sum>=dp[i][j],直接return ; 否则更新dp[i][j]——表示这是一个更优的解,然后继续递归!与sum的判断,每一个if条件都不能省!

/*  同种颜色可以直接跳上去;/0红色,1黄色,-1空格
    跳到不同颜色花费1金币;
   op=1, 或者跳到空格-1上,开销为2,然后 再跳到有色的地方--开销1或者0;*/
-----------------------------------------------------------------------------------
 

AC题解:

  

int m,n;   //和题意描述的相反,m表示有颜色的点数,n表示正方形的边长
int G[N][N];//存贮每个格点的颜色情况!
int ans;
int dir[][]={ {-,},{,},{,-},{,} }; int dp[N][N];//用DP[i][j]表示走到(i,j)时的最小代价 void dfs(int x,int y,int sum,int op,int col){
// printf("**(%d,%d) sum=%d op=%d col=%d\n",x,y,sum,op,col);
if(x==n&&y==n){
ans=min(ans,sum);
// printf("________sum=%d\n",sum);
return ;
}
for(int i=;i<;i++){
int dx=x+dir[i][];
int dy=y+dir[i][];
if(dx<||dy<||dx>n||dy>n)
continue;
if(sum>=dp[dx][dy])//进行优化,dp[][]记忆之前达到该点的最小花费!
continue ;
if(G[dx][dy]>=){
if(col==G[dx][dy]){//代价为零,同种颜色!
dp[dx][dy]=sum;
dfs(dx,dy,sum,,col);
}
else{ //代价为1,异种颜色,可以非一次!
dp[dx][dy]=sum+;
dfs(dx,dy,sum+,,!col);
}
}
else{
if(op==&&dp[dx][dy]>sum+ ){ //上面有条件:dp[dx][dy]>sum
dp[dx][dy]=sum+;
dfs(dx,dy,sum+,,col);//op改为1表示跳到空格上了,下一步要小心!
} } }
} int main(){ // freopen("checkerboard.in","r",stdin);
// freopen("checkerboard.out","w",stdout);
int x,y,z;
scanf("%d%d",&n,&m);
memset(G,-,sizeof(G));
for(int i=;i<=m;i++){
scanf("%d%d%d",&x,&y,&z);
G[x][y]=z;//0红色,1黄色
}
memset(vis,,sizeof(vis)); ans=inf;
memset(dp,inf,sizeof(dp));
dp[][]=;
dfs(,,,,G[][]);//省时需要记忆化搜索!! if(ans==inf){
printf("-1\n");
}
else{
printf("%d\n",ans);
}
return ;
}

(点开有注释呦~~)

【记忆化搜索】[NOIP-2017--普及组] -- 棋盘的更多相关文章

  1. 【NOIP 2017 普及组】 跳房子

    裸的单调队列优化dp+二分 我居然还调了挺久 日常审题错误 #include <bits/stdc++.h> using namespace std; typedef long long ...

  2. NOIP 2017 逛公园 记忆化搜索 最短路 好题

    题目描述: 策策同学特别喜欢逛公园.公园可以看成一张N个点MM条边构成的有向图,且没有 自环和重边.其中1号点是公园的入口,N号点是公园的出口,每条边有一个非负权值, 代表策策经过这条边所要花的时间. ...

  3. ACM International Collegiate Programming Contest, Tishreen Collegiate Programming Contest (2017)- K. Poor Ramzi -dp+记忆化搜索

    ACM International Collegiate Programming Contest, Tishreen Collegiate Programming Contest (2017)- K. ...

  4. 【noip 2009】 乌龟棋 记忆化搜索&动规

    题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩家控制一个乌龟棋子从起 ...

  5. 2017广东工业大学程序设计竞赛决赛 题解&源码(A,数学解方程,B,贪心博弈,C,递归,D,水,E,贪心,面试题,F,贪心,枚举,LCA,G,dp,记忆化搜索,H,思维题)

    心得: 这比赛真的是不要不要的,pending了一下午,也不知道对错,直接做过去就是了,也没有管太多! Problem A: 两只老虎 Description 来,我们先来放松下,听听儿歌,一起“唱” ...

  6. poj1191 棋盘分割【区间DP】【记忆化搜索】

    棋盘分割 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 16263   Accepted: 5812 Description ...

  7. POJ 1191 棋盘分割 【DFS记忆化搜索经典】

    题目传送门:http://poj.org/problem?id=1191 棋盘分割 Time Limit: 1000MS   Memory Limit: 10000K Total Submission ...

  8. 2017普及组D1T3 洛谷P3956 棋盘

    2017普及组D1T3 洛谷P3956 棋盘 原题 题目描述 有一个m×m的棋盘,棋盘上每一个格子可能是红色.黄色或没有任何颜色的.你现在要从棋盘的最左上角走到棋盘的最右下角. 任何一个时刻,你所站在 ...

  9. 最大联通子数组之和(dfs,记忆化搜索,状态压缩)

    最大联通子数组,这次的题目,我采用的方法为dfs搜索,按照已经取到的数v[][],来进行搜索过程的状态转移,每次对v[][]中标记为1的所有元素依次取其相邻的未被标记为1的元素,将其标记为1,然而,这 ...

随机推荐

  1. c# stmp邮件发送

    最近用到了邮件发送功能,因为stmp设置.参数传递错误等一些问题走了弯路,虽然代码很简单,这里还是记录一下,方便下次查阅. 用个人163邮箱测试的邮件发送 class Program { static ...

  2. idea创建自定义代码块

    1.File——>settings 2.找到Editor——>live Templates,点击加号+ 3.创建group或直接创建,我这里创建了一个user组,然后在user组里面添加l ...

  3. 034 Android NavigationView和DrawerLayout实现抽屉式导航设计(侧边栏效果)

    1.创建带侧滑效果的activity 右击,new---->activity---->选择NavgationDrawer Activity 2.xml文件布局 (1)activity_ma ...

  4. [.Net Core] - Asp.Net Core 编译成功,发布失败之解决

    背景 Asp.Net Core 项目编译成功,发布失败. 错误 Assets file 'D:\……\obj\project.assets.json' doesn't have a target fo ...

  5. STM32F103芯片SPI控制NRF24L012.4G无线模块交互通信实验

    1.NRF24L01模块的资料百度搜索一下就有很多.这里我就不做介绍本文主要侧重于应用层面实验介绍与分享. 2.先看下原理图. 根据原理图:写出NRF24L01  C语言驱动文件如下: #includ ...

  6. 随记sqlserver学习笔记(一)

    create database testuse test --部门表create table department( dept_id int not null identity primary key ...

  7. scrapy2——框架简介和抓取流程

    scrapy简介 ​ Scrapy是一个为了爬取网站数据,提取结构性数据而编写的应用框架. 可以应用在包括数据挖掘,信息处理或存储历史数据等一系列的程序中 scrapy的执行流程 Scrapy主要包括 ...

  8. django使用pyecharts(2)----django加入echarts_前后台分离

    二.Django 中使用 pyecharts. 前后端分离 1.安装 djangorestframework linux pip3 install djangorestframework window ...

  9. python 之 数据库(数据库安装方法、基本sql语句、存储引擎)

    第十章 数据库 10.1 数据库介绍 1.数据库相关概念 数据库服务器:本质就是一个台计算机,该计算机之上安装有数据库管理软件的服务端 数据库管理系统RDBMS:本质就是一个C/S架构的套接字软件 库 ...

  10. mysql全面整理(用于复习、查阅)--正在更新

    Mysql学习 1. 关键字与函数名称全部大写 2. 数据库名称.表名称.字段名称全部小写 3. SQL语句必须以分号结尾 一.数据库基本操作 1. 创建.查看数据库 CREATE {DATABASE ...