1.问题描述
有一个单入口,单出口的有向无环图。给出一个算法,在已有结点之间插入若干结点,使得从入口结点到出口结点经过的任意路径长度一致,详细描述你的算法思路,并分析其时间复杂度和空间复杂度。
2.算法思路
首先深度遍历,计算出入口到出口的最长路径,然后重新深度遍历,遍历到出口节点之前计算此路径长度,如果计算出小于最长路径则插入节点,使这个路径等于最长路径。
3.算法实现:(仅供参考)
struct Edge{ VPoint *dest; Edge *next; } struct VPoint{ int id; int weight; Edge *adj; } int longestDeep(VPoint *v , int visited[]) { int max=MIN,temp; VPoint *vp; if(v==NULL) return 0; visited[v->id]=1 for(Edge *ep=v->adj;;ep!=NULL;ep=ep->next) { vp=ep->dest; if(visited[vp->id]==0) { temp=longestDeep(vp); if(temp>max) max=temp; } } return max + 1; } int deepmax=longestDeep(v,visited); //O(n+e) O(1) Edge* insert(Edge *ep) { VPoint *newp = (VPoint*)malloc(VPoint); Edge *newe = (Edge *)malloc(Edge); init(newp); //初始化新节点 newp->adj=newe; newe->next=NULL; //新插结点的后续边的个数 必为一个 newe->dest=ep->dest; ep->dest=newp; return newe; } void extendPoint(VPoint *v, int visited[],int deep) // { if(v==NULL) return; visited[v->id]=1 for(Edge *ep=v->adj;ep!=NULL;ep=ep->next) { vp=ep->dest; if(visited[vp->id]==0) { deep++; if(vp->id==ENDID && deep+1 < deepmax) //? { int num=deepmax - (deep+1),i; for(i=1;i<=num;i++) ep = insert(ep); return; } extendPoint(vp,visited,deep); } } } //时间复杂度O(n+e) 空间复杂度O(1)