PTA—08-图8 How Long Does It Take (25分)

来源:互联网 发布:淘宝申请维修成功 编辑:程序博客网 时间:2024/05/16 17:14

今天状态很好。。。这题自己做一遍就AC了!先出给题目吧!


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 NN (\le 100100), the number of activity check points (hence it is assumed that the check points are numbered from 0 to N-1N1), and MM, the number of activities. Then MM 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".

Sample Input 1:

9 120 1 60 2 40 3 51 4 12 4 13 5 25 4 04 6 94 7 75 7 46 8 27 8 4

Sample Output 1:

18

Sample Input 2:

4 50 1 10 2 22 1 31 3 43 2 5

Sample Output 2:

Impossible


————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————

最近开始使用STL写算法了,一方面效率比较高,一方面也觉得这东西得学习下,上次CVTE的二面,问我用过Vector容器没,我说不知道实在尴尬。。。我是用MSVC的编译器的,但是PTA那个平台judge是用G++的,得把头文件改下!

这道题是拓扑排序的变形,插一句,作为工业工程专业,关键路径法之前也学习过,现在自己用程序语言描述还是挺不错的。

主要的思路是:

建图用邻接表来建,再建一个Indegree数组来保存入度值,当入度值为0的时候就是可以放进队列了。每处出列的话顺序没有要求,那就从小到大来pop,记得每次出列的时候更新邻接点的入度值和completetime!下面给出代码吧!(我给出的代码是在PTA上AC的代码,我写的时候是在VS2012平台上写的,因此还需要stafx头文件,然后那个scanf也得改成scanf_s)!



// 08-图8 How Long Does It Take   (25分).cpp : Defines the entry point for the console application.//#include <vector>#include <stdio.h>#include <queue>#define MaxVertex 100using namespace std;//采用邻接表来储存图typedef struct Node          //边表结点{int time,Nodenember;        };typedef struct VNode         //顶点的结构{int completedtime;vector<Node>edge;         //储存边结点};typedef VNode AdjList[MaxVertex];typedef struct ALGraph{int n,e;             //定点数和边数AdjList adjlist;};typedef ALGraph* PGraph;int main(){PGraph G=new ALGraph();int i,j,m,n,count=0,StartNode,EndNode,time;Node TmpNode;                    //临时储存边结点int* Indegree;scanf("%d%d",&(G->n),&(G->e));Indegree=new int[G->n];for(i=0;i<G->n;i++){Indegree[i]=0;                  //入度初始化G->adjlist[i].completedtime=0;  //每个点的时间归零}for(i=0;i<G->e;i++){scanf("%d%d%d",&StartNode,&EndNode,&time);TmpNode.Nodenember=EndNode;TmpNode.time=time;G->adjlist[StartNode].edge.push_back(TmpNode);}for(i=0;i<G->n;i++)                     //计算每个点的入度情况,放进Indegree数列{for(j=0;j<G->adjlist[i].edge.size();j++)Indegree[G->adjlist[i].edge[j].Nodenember]++;}queue<VNode>Q;for(i=0;i<G->n;i++)if(Indegree[i]==0){Q.push(G->adjlist[i]);count++;}while(!Q.empty()){VNode PopVNode=Q.front();              //取出队列第一个元素for(i=0;i<PopVNode.edge.size();i++)    //更新这个元素的邻接点的入度值和时间{m=G->adjlist[PopVNode.edge[i].Nodenember].completedtime;n=PopVNode.completedtime+PopVNode.edge[i].time;if(n>m)G->adjlist[PopVNode.edge[i].Nodenember].completedtime=n;if(--Indegree[PopVNode.edge[i].Nodenember]==0){Q.push(G->adjlist[PopVNode.edge[i].Nodenember]);count++;}}Q.pop();}if(count!=G->n){printf("Impossible");return 0;}int max=0;for(i=0;i<G->n;i++){if(G->adjlist[i].completedtime>max)max=G->adjlist[i].completedtime;}printf("%d",max);return 0;}


0 0