描述

Flappy Bird 是一款风靡一时的休闲手机游戏。玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度,让小鸟顺利通过画面右方的管道缝隙。如果小鸟一不小心撞到了水管或者掉在地上的话,便宣告失败。

图片

为了简化问题,我们对游戏规则进行了简化和改编:

游戏界面是一个长为 n,高为 m 的二维平面,其中有k 个管道(忽略管道的宽度)。

小鸟始终在游戏界面内移动。小鸟从游戏界面最左边 任意整数高度位置出发,到达游戏界面最右边时,游戏完成。

小鸟每个单位时间沿横坐标方向右移的距离为 1,竖直移动的距离由玩家控制。如果点击屏幕,小鸟就会上升一定高度 X,每个单位时间可以点击多次,效果叠加; 如果不点击屏幕,小鸟就会下降一定高度 Y。小鸟位于横坐标方向不同位置时,上 升的高度 X 和下降的高度 Y 可能互不相同。

小鸟高度等于 0 或者小鸟碰到管道时,游戏失败。小鸟高度为 m 时,无法再上升。

现在,请你判断是否可以完成游戏。如果可以,输出最少点击屏幕数;否则,输出小鸟最多可以通过多少个管道缝隙。

格式

输入格式

第 1 行有 3 个整数 n,m,k,分别表示游戏界面的长度,高度和水管的数量,每两个 整数之间用一个空格隔开;

接下来的 n 行,每行 2 个用一个空格隔开的整数 X 和 Y,依次表示在横坐标位置 0~n-1 上玩家点击屏幕后,小鸟在下一位置上升的高度 X,以及在这个位置上玩家不点击屏幕时, 小鸟在下一位置下降的高度 Y。

接下来 k 行,每行 3 个整数 P,L,H,每两个整数之间用一个空格隔开。每行表示一个管道,其中 P 表示管道的横坐标,L 表示此管道缝隙的下边沿高度为 L,H 表示管道缝隙上边沿的高度(输入数据保证 P 各不相同,但不保证按照大小顺序给出)。

输出格式

共两行。

第一行,包含一个整数,如果可以成功完成游戏,则输出 1,否则输出 0。 第二行,包含一个整数,如果第一行为 1,则输出成功完成游戏需要最少点击屏幕数,否则,输出小鸟最多可以通过多少个管道缝隙。

样例1

样例输入1[复制]

10 10 6

3 9

9 9

1 2

1 3

1 2

1 1

2 1

2 1

1 6

2 2

1 2 7

5 1 5

6 3 5

7 5 8

8 7 9

9 1 3

样例输出1[复制]

1

6

样例2

样例输入2[复制]

10 10 4

1 2

3 1

2 2

1 8

1 8

3 2

2 1

2 1

2 2

1 2

1 0 2

6 7 9

9 1 4

3 8 10

样例输出2[复制]

0

3



【题解】



完全背包(100)、多重背包(85分)、记忆化搜索(65分)、爆搜(50分)

记忆化搜索就是加个f[i][j]记录到i,j这个点的最小点击次数;

多重背包和完全背包也是

用一个f[i][j];

多重背包会好理解点

f[i][j] =min(f[i][j],f[i-1][j-k*a[i-1][0]]+1);

f[i][j] = min(f[i][j],f[i-1][j+a[i-1][1]]);

完全背包可以省去那个k层的循环

f[i][j] = min(f[i][j],f[i-1][j-a[i-1][0]]+1);

f[i][j] = min(f[i][j],f[i][j-a[i-1][0]]+1);

上面两步要紧接着写;(不懂就去看完全背包!);

下面这一步如果和上面那步一起写会造成错解;

f[i][j] = min(f[i][j],f[i-1][j+a[i-1][1]]);



【爆搜】(50分)

#include <cstdio>
#include <cstring>
#define MAXN 1001
#define MAXM 101 int n,m,k,a[MAXN][2],ans,maxstep=0;
bool bo[MAXN][MAXM],haved[MAXN]; void pre()
{
memset(bo,true,sizeof(bo));
} void input_data()
{
scanf("%d%d%d",&n,&m,&k);
ans=n*4;
for (int i=0;i<=n-1;i++)
scanf("%d%d",&a[i][0],&a[i][1]);
for (int i=1;i<=k;i++)
{
int x,down,up;
scanf("%d%d%d",&x,&down,&up);
haved[x]=true;
for (int j=1;j<=down;j++) bo[x][j]=false;
for (int j=up;j<=m;j++) bo[x][j]=false;
}
} void search(int xi,int highi,int toti,int numi)
{
int x=xi,high=highi,tot=toti,num=numi;
if (num>maxstep) maxstep=num;
if (tot>=ans) return;
if (x==n)
{
ans=tot;
return;
}
bool judge=false;
for (int i=1;i<=3;i++)
{
int temp=high+i*a[x][0];
if (temp>m)
{
temp=m;
judge=true;
}
if (bo[x+1][temp])
if (haved[x+1])
search(x+1,temp,tot+i,num+1);else
search(x+1,temp,tot+i,num);
if (judge) break;
}
int temp=high-a[x][1];
if ( temp>0 && bo[x+1][temp])
if (haved[x+1])
search(x+1,temp,tot,num+1);else
search(x+1,temp,tot,num);
} void pre_search()
{
for (int i=1;i<=m;i++)
search(0,i,0,0);
} void output_ans()
{
bool judge=ans==(n*4);
if (judge)
printf("%d\n%d\n",0,maxstep);
else
printf("%d\n%d\n",1,ans);
} int main()
{
//freopen("bird.in","r",stdin);
//freopen("bird.out","w",stdout);
pre();
input_data();
pre_search();
output_ans();
//fclose(stdin);
//fclose(stdout);
return 0;
}

【记忆化搜索】(65分)

#include <cstdio>
#include <cstring>
#define MAXN 10001
#define MAXM 1001 const int INF = 0x3f3f3f3f; int n,m,k,a[MAXN][2],ans,maxstep=0;
bool bo[MAXN][MAXM],haved[MAXN];
int f[MAXN][MAXM]; void pre()
{
memset(bo,true,sizeof(bo));
} void input_data()
{
scanf("%d%d%d",&n,&m,&k);
ans=n*4;
for (int i=0;i<=n-1;i++)
scanf("%d%d",&a[i][0],&a[i][1]);
for (int i=1;i<=k;i++)
{
int x,down,up;
scanf("%d%d%d",&x,&down,&up);
haved[x]=true;
for (int j=1;j<=down;j++) bo[x][j]=false;
for (int j=up;j<=m;j++) bo[x][j]=false;
}
} void search(int xi,int highi,int toti,int numi)
{
int x=xi,high=highi,tot=toti,num=numi;
if (f[x][high]<=toti)
return;
f[x][high] = tot;
if (num>maxstep) maxstep=num;
if (tot>=ans) return;
if (x==n)
{
ans = tot;
return;
}
bool judge=false;
for (int i=1;;i++)
{
int temp=high+i*a[x][0];
if (temp>=m)
{
temp=m;
judge=true;
}
if (bo[x+1][temp])
if (haved[x+1])
search(x+1,temp,tot+i,num+1);else
search(x+1,temp,tot+i,num);
if (judge) break;
}
int temp=high-a[x][1];
if ( temp>0 && bo[x+1][temp])
if (haved[x+1])
search(x+1,temp,tot,num+1);else
search(x+1,temp,tot,num);
} void pre_search()
{
for (int i=1;i<=m;i++)
search(0,i,0,0);
} void output_ans()
{
bool judge=ans==(n*4);
if (judge)
printf("%d\n%d\n",0,maxstep);
else
printf("%d\n%d\n",1,ans);
} int main()
{
//freopen("F:\\rush.txt","r",stdin);
memset(f,INF,sizeof(f));
pre();
input_data();
pre_search();
output_ans();
return 0;
}

【多重背包】(85分)

#include <cstdio>
#include <algorithm>
#include <cstring>
#define MAXN 10001
#define MAXM 1001 using namespace std; const int INF = 0x3f3f3f3f; int n,m,k,a[MAXN][2],ans,maxstep=0;
bool haved[MAXN];
int f[MAXN][MAXM];
int guan[MAXN][2]; void input_data()
{
scanf("%d%d%d",&n,&m,&k);
for (int i=0;i<=n-1;i++)
scanf("%d%d",&a[i][0],&a[i][1]);
for (int i=1;i<=k;i++)
{
int x,down,up;
scanf("%d%d%d",&x,&down,&up);
haved[x]=true;
guan[x][0] = down;
guan[x][1] = up;
}
} bool hefa(int x,int temp)
{
if (!haved[x] || (haved[x]&&guan[x][0]<temp && temp < guan[x][1]))
return true;
return false;
} int main()
{
//freopen("F:\\rush.txt","r",stdin);
memset(f,INF,sizeof(f));
input_data();
for (int i = 1;i <= m;i++)
f[0][i] = 0;
for (int i = 0;i <= n-1;i++)
{
bool added = false;
int down = 1,up = m;
if (haved[i])
down = guan[i][0]+1,up = guan[i][1]-1;
for (int j = down;j<= up;j++)
{
int ne = j-a[i][1];
if (ne>=1)
{
if (hefa(i+1,ne))
if (f[i+1][ne]>f[i][j])
{
f[i+1][ne] = f[i][j];
if (haved[i+1]&&!added)
{
added = true;
maxstep++;
}
}
}
for (int t = 1;;t++)
{
ne = j+t*a[i][0];
if (ne>=m)
ne = m;
if (hefa(i+1,ne))
{
if (f[i+1][ne]>f[i][j]+t)
{
f[i+1][ne] = f[i][j]+t;
if (haved[i+1]&&!added)
{
added = true;
maxstep++;
}
}
}
if (ne==m)
break;
}
}
}
// for (int i = m;i>=1;i--)
// printf("%d %d\n",f[1][i],f[2][i]);
// return 0;
int ans = f[n][1];
for (int i = 2;i <= m;i++)
ans = min(ans,f[n][i]);
if (ans < INF)
{
puts("1");
printf("%d\n",ans);
}
else
{
puts("0");
printf("%d\n",maxstep);
}
return 0;
}

【完全背包】(100分)

#include <cstdio>
#include <algorithm>
#include <cstring>
#define MAXN 10001
#define MAXM 1001 using namespace std; const int INF = 0x3f3f3f3f; int n,m,k,a[MAXN][2],ans,maxstep=0;
bool haved[MAXN];
int f[MAXN][MAXM];
int guan[MAXN][2]; void input_data()
{
scanf("%d%d%d",&n,&m,&k);
for (int i=0;i<=n-1;i++)
scanf("%d%d",&a[i][0],&a[i][1]);
for (int i=1;i<=k;i++)
{
int x,down,up;
scanf("%d%d%d",&x,&down,&up);
haved[x]=true;
guan[x][0] = down;
guan[x][1] = up;
}
} bool hefa(int x,int temp)
{
if (!haved[x] || (haved[x]&&guan[x][0]<temp && temp < guan[x][1]))
return true;
return false;
} int main()
{
//freopen("F:\\rush.txt","r",stdin);
memset(f,INF,sizeof(f));
input_data();
for (int i = 1;i <= m;i++)
f[0][i] = 0;
for (int i = 1;i <= n;i++)
{
bool added = false;
for (int j = 1;j <= m;j++)
{
if (j > a[i-1][0])
{
f[i][j] = min(f[i][j],f[i-1][j-a[i-1][0]]+1);
f[i][j] = min(f[i][j],f[i][j-a[i-1][0]]+1);
}
if (j==m)
{
for (int t = m-a[i-1][0];t <= m;t++)
{
f[i][j] = min(f[i][j],f[i-1][t]+1);
f[i][j] = min(f[i][j],f[i][t]+1);
}
}
}
int down = 1,up = m;
if (haved[i])
down = guan[i][0]+1,up = guan[i][1]-1;
for (int j = down;j<= up;j++)
{
int pre = j+a[i-1][1];
if (pre<=m)
{
if (hefa(i-1,pre))
f[i][j] = min(f[i][j],f[i-1][pre]);
}
if (haved[i] && f[i][j]<INF && !added)
{
added = true;
maxstep++;
}
}
if (haved[i])
{
for (int j = 1;j <= guan[i][0];j++)
f[i][j] = INF;
for (int j = guan[i][1];j <= m;j++)
f[i][j] = INF;
}
}
int ans = f[n][1];
for (int i = 2;i <= m;i++)
ans = min(ans,f[n][i]);
if (ans < INF)
{
puts("1");
printf("%d\n",ans);
}
else
{
puts("0");
printf("%d\n",maxstep);
}
return 0;
}

【25.00%】【vijos P1907】飞扬的小鸟的更多相关文章

  1. P1907飞扬的小鸟

    P1907飞扬的小鸟 描述 Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度,让小鸟顺利通过画面右方的管道缝隙.如果小鸟一不小心撞到了水管或 ...

  2. vijos 1907 飞扬的小鸟

    我心里毫无波动甚至还有点想笑. WTF WTF WTF WTF WTF WTF WTF GTMD调了一天什么鬼啊. 原来更新的范围有讲究啊. #include<iostream> #inc ...

  3. 洛谷 P1941 飞扬的小鸟

    洛谷 P1941 飞扬的小鸟 原题链接 首先吐槽几句 noip都快到了,我还不刷起联赛大水题! 题目描述 Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节 ...

  4. Codevs 3729==洛谷P1941 飞扬的小鸟

    P1941 飞扬的小鸟 456通过 2.4K提交 题目提供者该用户不存在 标签动态规划2014NOIp提高组 难度提高+/省选- 提交该题 讨论 题解 记录   题目描述 Flappy Bird 是一 ...

  5. Codevs 3729 飞扬的小鸟

    飞扬的小鸟 标签 动态规划 NOIp提高组 2014 难度 提高+/省选- 题目描述 Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度,让小 ...

  6. [NOIP2014][DP]飞扬的小鸟

    [NOIP2014]飞扬的小鸟 ——!x^n+y^n=z^n 题目描述: Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度,让小鸟顺利通过画 ...

  7. [NOIP2014]飞扬的小鸟[DP]

    [NOIP2014]飞扬的小鸟 ——!x^n+y^n=z^n 题目描述: Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度,让小鸟顺利通过画 ...

  8. [codevs3729]飞扬的小鸟

    [codevs3729]飞扬的小鸟 试题描述 输入 输出 输出文件名为 bird.out. 共两行. 第一行,包含一个整数,如果可以成功完成游戏,则输出 1,否则输出 0. 第二行,包含一个整数,如果 ...

  9. NOIP2014 飞扬的小鸟

    3. 飞扬的小鸟 (bird.cpp/c/pas) [问题描述] Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度,让小鸟顺利通过画面右方的 ...

  10. Luogu 1941 【NOIP2014】飞扬的小鸟 (动态规划)

    Luogu 1941 [NOIP2014]飞扬的小鸟 (动态规划) Description Flappy Bird 是一款风靡一时的休闲手机游戏.玩家需要不断控制点击手机屏幕的频率来调节小鸟的飞行高度 ...

随机推荐

  1. 2 Java基础语法(keyword,标识符,凝视,常量,进制转换,变量,数据类型,数据类型转换)

    1:keyword(掌握) (1)被Java语言赋予特定含义的单词 (2)特点: 所有小写. (3)注意事项: A:goto和const作为保留字存在. B:类似于Notepad++这种高级记事本会对 ...

  2. Tomcat源代码阅读#1:classloader初始化

    Bootstrap 通过Tomcat的启动脚本能够看到启动的入口是在Bootstrap,来看下Bootstrap的main方法, /** * Main method and entry point w ...

  3. asp.net--TextBox属性全研究

    . .aspx代码例如以下: <%@ Page Language="C#" AutoEventWireup="true" CodeFile="T ...

  4. javascript中的事件问题的总结

    一.什么是事件? 事件就是DOM和浏览器之间的交互行为(只要触发了这个行为,也就相当于触发了事件),我们可以通过事件监听来绑定事件,例如:box.onclick=function(){},如果我们点击 ...

  5. tensorflow 的 Batch Normalization 实现(tf.nn.moments、tf.nn.batch_normalization)

    tensorflow 在实现 Batch Normalization(各个网络层输出的归一化)时,主要用到以下两个 api: tf.nn.moments(x, axes, name=None, kee ...

  6. WM_CAP_DRIVER_CONNECT

    WM_CAP_DRIVER_CONNECT //ActiveX ---->OnCreate m_pit.Create(IDD_CAM_DIALOG,this);  CRect rc;  this ...

  7. matlab 程序发布

    将matlab程序发布为可执行程序包 说明,这种可执行程序包可以在没有安装matlab的计算机上运行. 1. 打开Applicaiton Compler 如果下拉列表中没有这个APPLICATIOND ...

  8. [React] Use React.cloneElement to Modify and Add Additional Properties to React Children

    In this lesson we'll show how to use React.cloneElement to add additional properties to the children ...

  9. php面试题10(复习)

    php面试题10(复习) 一.总结 复习 二.php面试题10 21.谈谈 asp,php,jsp 的优缺点(1 分)(asp要钱,jsp学习成本大)答:ASP 全名 Active Server Pa ...

  10. js中ajax连接服务器open函数的另外两个默认参数get请求和默认异步(open的post方式send函数带参数)(post请求和get请求区别:get:快、简单 post:安全,量大,不缓存)(服务器同步和异步区别:同步:等待服务器响应当中浏览器不能做别的事情)(ajax和jquery一起用的)

    js中ajax连接服务器open函数的另外两个默认参数get请求和默认异步(open的post方式send函数带参数)(post请求和get请求区别:get:快.简单 post:安全,量大,不缓存)( ...