# include<iostream>
# include<queue>
# include<cstring>
# include<stack>
using namespace std;
const int maxn=100+5;
typedef struct arcnode{
int adjnode;
int weight;
arcnode *nextarc;
}arcnode;
typedef struct vnode{
int data;
arcnode *firstarc;
}vnode;
typedef struct graph{
vnode vertexs[maxn];
int vertexnum; //顶点数目
int edgenum; //边数目
}graph;
queue<int> q; //存放入度为0的顶点索引
stack<int> ss; //存放拓扑排序的逆序列
int indegree[maxn];
int ve[maxn];//事件最早发生时间
int vl[maxn];// 事件最迟发生时间
int e[maxn];//活动最早发生时间
int l[maxn];//活动最迟发生时间
int find(graph g,int v)
{
for(int i=0;i<g.vertexnum;i++)
{
if(g.vertexs[i].data==v)
return i;
}
}
void init(graph &g)
{
cin>>g.vertexnum>>g.edgenum;
for(int i=0;i<g.vertexnum;i++)
{
cin>>g.vertexs[i].data;
g.vertexs[i].firstarc=NULL;
}
int u,v,w;
for(int i=0;i<g.edgenum;i++)
{
cin>>u>>v>>w;
arcnode *s=new arcnode();
int index_u=find(g,u);
int index_v=find(g,v);
s->adjnode=index_v;
s->weight=w;
s->nextarc=g.vertexs[index_u].firstarc;
g.vertexs[index_u].firstarc=s;
}
}
void findindegree(graph g)
{
for(int i=0;i<g.vertexnum;i++)
{
for(int j=0;j<g.vertexnum;j++)
{
if(i!=j)
{
arcnode* s=g.vertexs[j].firstarc;
while(s)
{
if(s->adjnode==i)
{
indegree[i]++;
break;
}
s=s->nextarc;
}
}
}
}
}
bool topulogical(graph g)
{
int cnt=0;
for(int i=0;i<g.vertexnum;i++)
{
if(!indegree[i]) //入度为0的入队列
q.push(i);
ve[i]=0; //初始化事件最早开始时间
}
while(!q.empty())
{
int k=q.front();
q.pop();
ss.push(k);
cnt++;
arcnode* s=g.vertexs[k].firstarc;
while(s)
{
int j=s->adjnode;
indegree[j]--;
if(!indegree[j])
q.push(s->adjnode);
if(ve[k]+s->weight>ve[j]) //松弛
ve[j]=ve[k]+s->weight;
s=s->nextarc;
}
}
if(cnt<g.vertexnum)
return false;
return true;
}
void criticalpath(graph g)
{
if(!topulogical(g))
{
cout<<"存在回路"<<endl;
return ;
}
for(int i=0;i<g.vertexnum;i++)
{
vl[i]=ve[g.vertexnum-1]; //初始化事件最迟开始时间,等于汇点的最早开始时间,
//当然除汇点以外的点的最迟开始时间也可初始化为某一最大值
}
while(!ss.empty())
{
int k=ss.top();
ss.pop();
arcnode *s=g.vertexs[k].firstarc;
while(s)
{
int j=s->adjnode;
if(vl[j]-s->weight<vl[k])
vl[k]=vl[j]-s->weight;
s=s->nextarc;
}
}
for(int j=0;j<g.vertexnum;j++)
{
arcnode *s=g.vertexs[j].firstarc;
while(s)
{
int k=s->adjnode;
int w=s->weight;
int ee=ve[j];
int el=vl[k]-w;
if(ee==el)
cout<<"V"<<g.vertexs[j].data<<"->"<<"V"<<g.vertexs[k].data<<"dis"<<w<<" "<<endl;
s=s->nextarc;
}
}
}
int main()
{
graph g;
init(g);
memset(indegree,0,sizeof(indegree));
findindegree(g);
criticalpath(g);
return 0;
}
关键路径(CRITICALPATH 邻接表建图)
最新推荐文章于 2021-06-12 09:42:24 发布