回溯法求最佳工作分配方案

这个问题是典型的回溯法,比八皇后问题简化一点,重要的是其中一个部分:在深搜过程中要进行值的判断,来决定是否停止当前的搜索,这对以减少运行时间十分重要,一开始我没有考虑这个问题,就导致很多样例都超时了。

 

题目如下:

有 n 份工作要分配给 n 个人来完成,每个人完成一份。第 i 个人完成第 k 份工作所用的时间为一个正整数 tik,其中1 ≤ i, k ≤ n。试确定一个分配方案,使得完成这 n 份工作的时间总和最小。

输入

输入包含 n + 1 行。

第 1 行为一个正整数 n。

第 2 行到第 n + 1 行中每行都包含 n 个正整数,形成了一个 n × n 的矩阵。在该矩阵中,第 i 行第 k 列元素 tik 表示第 i 个人完成第 k 件工作所要用的时间。

输出

1 行,包含一个正整数,表示所有分配方案中最小的时间总和。

输入样例

5
9 2 9 1 9
1 9 8 9 6
9 9 9 9 1
8 8 1 8 4
9 1 7 8 9

输出样例

5

限制

1 ≤ n ≤ 15

1 ≤ tik ≤ 10^4

代码如下

#include <iostream>

using namespace std;
int N;
int people_work[15][15];
int vis[15]={0};
int cur[15];
int min_time;
int total=0;
void cal_min_time(int num){
    if(num==N){
        if(min_time==-1||total<min_time){
            min_time=total;
        }
    }
    else{
        for(int i=0;i<N;i++){
            if(!vis[i]){
                total+=people_work[num][i];
                if(min_time!=-1&&total>min_time){
                    total-=people_work[num][i];
                    continue;
                }
                vis[i]=1;
                cal_min_time(num+1);
                total-=people_work[num][i];
                vis[i]=0;
            }
        }
    }
}
int main()
{
    cin>>N;
    for(int i=0;i<N;i++){
        for(int j=0;j<N;j++){
            cin>>people_work[i][j];
        }
    }
    min_time=-1;
    cal_min_time(0);
    cout<<min_time;
    return 0;
}

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值