Acwing 165.小猫爬山【DFS】【剪枝】

1.题目
题目链接:点击这里

2.解决思路
尽量减少缆车的使用;从0个缆车开始,对于每一只猫咪,如果当前的num个缆车中还有某个缆车能装得下,则把这只猫咪装到这个缆车中,该缆车容积sum减少掉猫咪体重;如果当前num个缆车没有能装下当前猫咪的,则需要新租一个缆车,num++;DFS的过程中,状态空间树上的某个节点若出现num>ans,这个分支也没有继续下去的必要了,剪枝。

3.代码

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>

using namespace std;
const int MAXN=20,INF=0x3f3f3f3f;

int weight[MAXN];
int n,w,ans=2e9;
int sum[MAXN];
bool st[MAXN];

void dfs(int u,int num)//u小猫编号,num需要缆车数量,cur最后一个未装满的缆车已经装了多少
{
    
    
    if(num>=ans) return;
    if(u>n){
    
    
        ans=num;
        return;
    }
    
    for(int i=1;i<=num;i++){
    
    //前num个缆车可以装得下
        if(sum[i]+weight[u]<=w){
    
    
            sum[i]+=weight[u];
            dfs(u+1,num);
            sum[i]-=weight[u];
        }
    }
    
    //前num个缆车装不下,需要新缆车
    sum[num+1]+=weight[u];
    dfs(u+1,num+1);
    sum[num+1]-=weight[u];
}

int main(void)
{
    
    
    cin>>n>>w;
    
    for(int i=1;i<=n;i++) cin>>weight[i];//猫猫体重
    
    memset(st,false,sizeof(st));
    dfs(1,0);
    
    cout<<ans<<endl;
    
    return 0;
}

猜你喜欢

转载自blog.csdn.net/qq_43579980/article/details/120196481