第六节 搜索专题 - 2

A. 小木棍

时间:1 空间:32M

题目描述:

乔治有一些同样长的小木棍,他把这些木棍随意砍成几段,直到每段的长都不超过 \(50\) 。现在,他想把小木棍拼接成原来的样子,但是却忘记了自己开始时有多少根木棍和它们的长度。给出每段小木棍的长度,编程帮他找出原始木棍的最小可能长度。

输入格式:

第一行为一个单独的整数 \(N\) 表示砍过以后的小木棍的总数。 第二行为 \(N\) 个用空格隔开的正整数,表示 \(N\) 根小木棍的长度。

输出格式:

输出仅一行,表示要求的原始木棍的最小可能长度。

样例输入1:

9
5 2 1 5 2 1 5 2 1

样例输出1:

6

约定: \(1 \le n \le 60\)

点击查看代码
#include<iostream>
using namespace std;

int n, a[105], maxn = -1e9, minn = 1e9;
int x;
long long sum = 0;

void dfs(int res, int num, int target) {
	if(!res) {
		cout << target << endl;
		exit(0);
	}
	if(num == target) {
		dfs(res - 1, 0, target);
		return;
	}
	for(int i = maxn; i >= minn; i --) {
		if(!a[i]) continue;
		if(i + num <= target) {
			a[i] --;
			dfs(res, num + i, target);
			a[i] ++;
			if(!num || num + i == target) break;
		}
	}
}

int main() {
	cin >> n;
	for(int i = 1; i <= n; i ++) {
		cin >> x;
		a[x] ++;
		maxn = max(maxn, x);
		minn = min(minn, x);
		sum += x;
	}
	x = sum >> 1;
	for(int i = maxn; i <= x; i ++) {
		if(sum % i) continue;
		dfs(sum / i, 0, i);
	}
	cout << sum << endl;
	return 0;
}
编译结果
compiled successfully
time: 7ms, memory: 3508kb, score: 100, status: Accepted
> test 1: time: 0ms, memory: 3364kb, points: 10, status: Accepted
> test 2: time: 0ms, memory: 3412kb, points: 10, status: Accepted
> test 3: time: 1ms, memory: 3464kb, points: 10, status: Accepted
> test 4: time: 0ms, memory: 3396kb, points: 10, status: Accepted
> test 5: time: 0ms, memory: 3464kb, points: 10, status: Accepted
> test 6: time: 1ms, memory: 3456kb, points: 10, status: Accepted
> test 7: time: 0ms, memory: 3356kb, points: 10, status: Accepted
> test 8: time: 4ms, memory: 3508kb, points: 10, status: Accepted
> test 9: time: 0ms, memory: 3452kb, points: 10, status: Accepted
> test 10: time: 1ms, memory: 3404kb, points: 10, status: Accepted

B. 骨头的诱惑

题目描述:

在一个迷宫里面有一只小狗发现了一根骨头,现在他准备逃出迷宫,迷宫中只有一个地方有门可以出去,而且这个门只会在T秒的时候打开,开了之后下一时刻就会关闭。每移动一步要花费 \(1\) 秒,规定不能停留在某一个位置上,即走到一个位置要立刻前往下一个位置。每个位置不能重复走。假设小狗很聪明,它能成功逃出迷宫么?

输入格式:

第一行输入三个整数 \(n\), \(m\), \(T\),表示迷宫的尺寸以及门打开的时间

接下来 \(n\) 行每行 \(m\) 个字符,表示迷宫中每一个位置上的信息。

'X': 表示墙,不能进入

'S': 小狗现在的位置

'D': 门

'.': 空地

输出格式:

根据能否成功逃离,输出 “YES” 或者 “NO”

样例输入1:

4 4 5
S.X.
..X. 
..XD 
....

样例输出1:

NO

样例输入2:

3 4 5 
S.X. 
..X. 
...D

样例输出2:

YES

约定: \(1 < n,m < 7\), \(0 < T < 50\)

点击查看代码
#include<iostream>
using namespace std;

int n, m, t, sx, sy, ex, ey;
bool vis[10][10];
char mp[10][10];
int dx[4] = { 0, -1, 0, 1 };
int dy[4] = { 1, 0, -1, 0 };

bool dfs(int x, int y, int T) {
	if(abs(x - ex) + abs(y - ey) > T) return false;
	if(x == ex && y == ey && !T) return true;
	bool flag = false;
	for(int i = 0; i < 4; i ++) {
		int xx = x + dx[i], yy = y + dy[i];
		if(xx <= n && xx >= 1 && yy <= m && yy >= 1 && !vis[xx][yy] && mp[xx][yy] != 'X') {
			vis[xx][yy] = true;
			flag = flag || dfs(xx, yy, T - 1);
			vis[xx][yy] = false;
		}
	}
	return flag;
}

int main() {
	cin >> n >> m >> t;
	for(int i = 1; i <= n; i ++)
		for(int j = 1; j <= m; j ++) {
			cin >> mp[i][j];
			if(mp[i][j] == 'S') sx = i, sy = j;
			if(mp[i][j] == 'D') ex = i, ey = j;
		}
	if(sx + sy + ex + ey + t & 1) {
		cout << "NO\n";
		return 0;
	}
	vis[sx][sy] = true;
	if(dfs(sx, sy, t)) cout << "YES\n";
	else cout << "NO\n";
	return 0;
}
编译结果
compiled successfully
time: 756ms, memory: 3504kb, score: 100, status: Accepted
> test 1: time: 74ms, memory: 3392kb, points: 10, status: Accepted
> test 2: time: 0ms, memory: 3396kb, points: 10, status: Accepted
> test 3: time: 74ms, memory: 3412kb, points: 10, status: Accepted
> test 4: time: 74ms, memory: 3412kb, points: 10, status: Accepted
> test 5: time: 0ms, memory: 3216kb, points: 10, status: Accepted
> test 6: time: 7ms, memory: 3348kb, points: 10, status: Accepted
> test 7: time: 0ms, memory: 3348kb, points: 10, status: Accepted
> test 8: time: 526ms, memory: 3504kb, points: 10, status: Accepted
> test 9: time: 1ms, memory: 3376kb, points: 10, status: Accepted
> test 10: time: 0ms, memory: 3352kb, points: 10, status: Accepted
posted @ 2023-07-15 12:28  So_noSlack  阅读(157)  评论(0)    收藏  举报