Acwing165 --- 小猫爬山(DFS)

该篇文章介绍了一种编程方法,通过使用深度优先搜索(DFS)算法解决了一个关于小猫爬山后如何以最少费用乘坐索道下山的问题,涉及到数组排序和权重分配优化。
摘要由CSDN通过智能技术生成

翰翰和达达饲养了 N 只小猫,这天,小猫们要去爬山。

经历了千辛万苦,小猫们终于爬上了山顶,但是疲倦的它们再也不想徒步走下山了(呜咕>_<)。

翰翰和达达只好花钱让它们坐索道下山。

索道上的缆车最大承重量为 W,而 N 只小猫的重量分别是 C1、C2……CN。

当然,每辆缆车上的小猫的重量之和不能超过 W。

每租用一辆缆车,翰翰和达达就要付 1 美元,所以他们想知道,最少需要付多少美元才能把这 N 只小猫都运送下山?

输入格式

第 1 行:包含两个用空格隔开的整数,N 和 W。

第 2..N+1行:每行一个整数,其中第 i+1 行的整数表示第 i 只小猫的重量 Ci。

输出格式

输出一个整数,表示最少需要多少美元,也就是最少需要多少辆缆车。

数据范围

1≤N≤18,
1≤Ci≤W≤108

输入样例:
5 1996
1
2
1994
12
29
输出样例:
2

对于这种问题肯定有限选择暴力枚举,那么我们在枚举前需要将其从大到小排列,以便于枝叶最小。

随后分析当前情况,无非就是加车or不加车(这里不加车就需要判断当前是否可以加小猫)。

于是我们先判断如果不加车的情况,不加车先利用for循环枚举小猫,然后判断小猫是否可以被装车,因为这里咱们要考虑车的问题,所以dfs参数就需要记录当前是第几只猫被装入以及当前共有多少辆缆车,随后利用数组cab记录每一辆的缆车所承载重量为了方便判断缆车是否都可以装入小猫,注意这里因为是枚举每一种情况,所以我们需要回溯一下

然后我们就需要加车了,因为要加车的情况肯定是当前第x个小猫无法被装入,所以我们就要让x + 1并让缆车总数num+1。

#include <iostream>
#include <algorithm>
using namespace std;
const int N = 100;
int a[N],cab[N];	//a数组为小猫重量,cab数组记录对应的缆车目前占有的重量
int n,w;
int ans = 20;
void dfs(int x , int num)
{
	if(num >= ans)  return ;
    if(x > n)  
	{
		ans = min(ans , num);
		return ;
	}                                            
	for(int i = 1;i <= num;i++)
	{
		if(cab[i] + a[x] <= w)
		{
			cab[i] += a[x];
			dfs(x + 1,num);
			cab[i] -= a[x];
		}
	}
	cab[num + 1] = a[x];
	dfs(x + 1,num + 1);
	cab[num + 1] = 0;
}
int main()
{

	cin >> n >> w;
	for(int i = 0;i < n;i++)
	    cin >> a[i];
	sort(a , a + n);
	reverse(a , a + n);
	dfs(0,0);
	cout << ans;
	return 0;
}

  • 9
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

记得开心一点嘛

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值