7-12 How Long Does It Take

Given the relations of all the activities of a project, you are supposed to find the earliest completion time of the project.

Input Specification:

Each input file contains one test case. Each case starts with a line containing two positive integers N (100), the number of activity check points (hence it is assumed that the check points are numbered from 0 to N1), and M, the number of activities. Then M lines follow, each gives the description of an activity. For the i-th activity, three non-negative numbers are given: S[i]E[i], and L[i], where S[i] is the index of the starting check point, E[i] of the ending check point, and L[i] the lasting time of the activity. The numbers in a line are separated by a space.

Output Specification:

For each test case, if the scheduling is possible, print in a line its earliest completion time; or simply output "Impossible".

知识点:拓扑排序

思路:

建一个图‘pre’,记录每一个节点的前节点;建一个图‘Graph’,记录每一个节点的后节点

建一个队列,每次操作后,入度(indegree)为0的节点入队

  • 注意多个起点和终点的问题:
    • 完成后扫描最大的cost输出
  • 有回路问题
    • 遍历的节点数<总节点数,即有回路
#include <iostream>
#include <vector>
#include <queue>
using namespace std;
const int maxn = 105;

int n,m;
struct edge{
    int v;
    int time;    
};
vector<edge> pre[maxn];
vector<int> Graph[maxn];
int cost[maxn];
int indegree[maxn];

void check(int start,int end){
    int cnt=0;
    fill(cost,cost+maxn,0);
    queue<int> q;
    for(int i=0;i<n;i++){ // indegree==0 的入队
        if(indegree[i]==0){    
            q.push(i);
        }
    }
    int tmp;
    while(q.size()){ // 按照拓扑序搜索
        tmp = q.front();
        cnt++;
        q.pop();
        cost[tmp] = 0;
        for(int i=0;i<pre[tmp].size();i++){
            if((pre[tmp][i].time+cost[pre[tmp][i].v]) > cost[tmp]){
                cost[tmp] = (pre[tmp][i].time+cost[pre[tmp][i].v]);
            }
        }
        for(int i=0;i<Graph[tmp].size();i++){
            indegree[Graph[tmp][i]]--;
            if(indegree[Graph[tmp][i]]==0){
                q.push(Graph[tmp][i]);
            }
        }
    }
    int endtime = 0;
    if(cnt!=n) printf("Impossible
");
    else{
        for(int i=0;i<n;i++){
            if(cost[i]>endtime){
                endtime=cost[i];
            }
        }
        printf("%d
",endtime);
    }
}

int main(int argc, char *argv[]) {
    scanf("%d %d",&n,&m);
    int a,b,t;
    struct edge newedge;
    int flag[maxn];
    fill(flag,flag+maxn,0);
    for(int i=0;i<m;i++){
        scanf("%d %d %d",&a,&b,&newedge.time);
        indegree[b]++;
        newedge.v = a;
        flag[a] = 1;
        pre[b].push_back(newedge);
        Graph[a].push_back(b);
    }
    int start,end;
    for(int i=0;i<n;i++){
        if(flag[i]==0){
            end = i;
        }
        if(pre[i].size()==0){
            start = i;
        }
    }
    //printf("%d %d",start,end);
    check(start,end);
}

Sample Input 1:

9 12
0 1 6
0 2 4
0 3 5
1 4 1
2 4 1
3 5 2
5 4 0
4 6 9
4 7 7
5 7 4
6 8 2
7 8 4

Sample Output 1:

18

Sample Input 2:

4 5
0 1 1
0 2 2
2 1 3
1 3 4
3 2 5

Sample Output 2:

Impossible


原文地址:https://www.cnblogs.com/lokwongho/p/9836539.html