打卡信奥刷题(1548)用C++实现信奥 P6285 [COCI 2016/2017 #1] Jetpack

P6285 [COCI 2016/2017 #1] Jetpack

题目描述

Mirko 正在玩一款小游戏。在一个 10 10 10 n n n 列的矩阵中,他需要从左下角出发,避免在障碍物处停留,最终到达第 n n n 列的任意位置。每秒,他都会向右移动一个单位。

在游戏中,Mirko 拥有一个喷气背包(游戏开始时关闭):

  • 打开喷气背包时,每秒他将额外向上移动一个单位(即向右上方移动),直到他处于矩阵顶端的一行。
  • 关闭喷气背包时,每秒他将额外向下移动一个单位(即向右下方移动),直到他处于矩阵底端的一行。

他可以在任意一秒打开喷气背包,并在任意秒后关闭。将此记为一次操作。

现在,Mirko 想让你设计一系列操作,使他能够顺利结束游戏。

输入格式

第一行一个整数 n n n,表示矩阵的列数。

接下来 10 10 10 行,每行 n n n 个字符。表示相应位置是否存在障碍物。字符只可能是 .X

  • . 表示该区域不存在障碍物。
  • X 表示该区域存在障碍物。

输出格式

本题使用 Special Judge

第一行一个非负整数 p p p,表示 Mirko 应进行操作的次数。

接下来 p p p 行,每行两个正整数 t i t_i ti x i x_i xi,表示 Mirko 需要在第 t i t_i ti 秒打开喷气背包,并在 x i x_i xi 秒后关闭。

若存在多种答案,请输出任意一种。

另外:

  • 操作应按时间顺序给出,且在一次操作完成前无法进行其他操作。即 t i + x i ≤ t i + 1 t_i+x_i\le t_{i+1} ti+xiti+1
  • 游戏结束后 Mirko 无法进行任何操作。即 t i < n t_i<n ti<n
  • Mirko 不希望操作次数过多。即 0 ≤ p ≤ 5 × 10 4 0\le p\le 5\times 10^4 0p5×104

输入输出样例 #1

输入 #1

11
.....XX...X
....XX...XX
...XX...XX.
...........
....XXX....
...........
.....X.....
....XX...X.
...XX...XX.
...X...XX..

输出 #1

2
1 4
7 2

输入输出样例 #2

输入 #2

20
X..................X
.X................X.
..X..............X..
...X............X...
....X..........X....
.....X........X.....
......X......X......
.......X....X.......
........X..X........
.........XX.........

输出 #2

1
8 10

说明/提示

样例 1 解释

下图为样例输出一所表示的路径。

.....XX...X
....XX...XX
...XX...XX.
...........
....XXX....
.....*...*.
....*X*.*.*
...*XX.*.X.
..*XX...XX.
**.X...XX.. 

数据规模与约定

对于 100 % 100\% 100% 的数据,保证 1 ≤ n ≤ 10 5 1\le n\le 10^5 1n105

数据保证至少存在一种方案,能使得 Mirko 能够顺利结束游戏。


说明

题目译自 COCI2016-2017 CONTEST #1 T2 Jetpack

C++实现

#include<bits/stdc++.h>
using namespace std;
const int N = 1e5+5;
int n,out[N][2],cnt;
char a[11][N];
bool v[N],vis;
void init(){
	ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
	cin>>n;
	for(int i = 1;i<=10;i++)
		for(int j = 1;j<=n;j++)
			cin>>a[i][j];
}
void print(){
	for(int i = 1;i<=n;i++)
		if(v[i-1]==0&&v[i])
        out[++cnt][0] = i-1,out[cnt][1] = 1;
		else if(v[i]) out[cnt][1]++;
	cout<<cnt<<'\n';
	for(int i = 1;i<=cnt;i++)
		cout<<out[i][0]<<' '<<out[i][1]<<'\n';
}
bool dfs(int x,int y){
	if(vis) return 1;
	if(y==n)
		return vis = 1;
	if(a[x][y]=='X') return 0;
	a[x][y] = 'X';
	if(dfs(max(1,x-1),y+1))
		return v[y] = 1;
	if(vis) return 1;
	if(dfs(min(x+1,10),y+1))
		return 1;
	return vis;
}
int main()
{
	init();
	dfs(10,1);
	print();
	return 0;
}

在这里插入图片描述

后续

接下来我会不断用C++来实现信奥比赛中的算法题、GESP考级编程题实现、白名单赛事考题实现,记录日常的编程生活、比赛心得,感兴趣的请关注,我后续将继续分享相关内容

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值