这里的拓扑排序都是用优先队列实现优化
拓扑排序确定有向图点的出现顺序, 同时判断有向图是否有环
链式前向星
class TopologicalSort_AdjicencyList {
public:
static const int MAXN = 5e2+10 ;
static const int MAXM = 2e3+10;
int st, ed; /* int cntOfVertex; */
struct EDGE {
int v, to;
}e[MAXM];
int head[MAXM], cnt;
inline void add ( int u, int v ) {
e[cnt].v = v, e[cnt].to = head[u]; head[u] = cnt++; inDegree[v]++;
}
int inDegree[MAXN]; /* int ans[MAXN]; */
TopologicalSort_AdjicencyList ( ) { };
TopologicalSort_AdjicencyList ( int _st, int _ed ) : st( _st ), ed( _ed ) { };
void ini ( int st, int ed ) {
this->st = st, this->ed = ed;
/* cntOfVertex = 0; */
cnt = 0;
memset( head, -1, sizeof(head) );
memset( inDegree , 0 , sizeof(inDegree) ) ;
/* memset( ans , 0 , sizeof(ans) ) ; */
}
bool run ( ) {
int cntOfZeroDegree = 0;
/* cntOfVertex = 0; */
priority_queue<int, vector<int>, greater<int> >q; //当要求编号小的优先输出时用优先队列存储点
while ( !q.empty() ) q.pop();
for ( int i = st; i < ed+1; ++i )
if ( !inDegree[i] )
q.push( i );
while ( !q.empty() ) {
int u = q.top();
q.pop();
cntOfZeroDegree++;
// ans[cntOfVertex++] = u;
for ( int k = head[u]; k != -1; k = e[k].to ) {
int v = e[k].v;
inDegree[v]--;
if ( !inDegree[v] ) q.push( v );
}
}
return cntOfZeroDegree!=(ed-st+1); // 真为有环
}
}tp;
邻接矩阵
class TopologicalSort_Matrix {
public:
static const int MAXN = 1e2+10 ;
int st, ed; /* int cntOfVertex; */
int graph[MAXN][MAXN], inDegree[MAXN]; /* int ans[MAXN]; */
TopologicalSort_Matrix ( ) { };
TopologicalSort_Matrix ( int _st, int _ed ) : st( _st ), ed( _ed ) { };
inline void add ( int u, int v ) {
if ( !graph[u][v] ) { // 处理重边
graph[u][v] = 1 ;
inDegree[v]++ ;
}
}
void ini ( int st, int ed ) {
this->st = st, this->ed = ed;
// cntOfVertex = 0;
memset( graph , 0 , sizeof(graph) );
memset( inDegree , 0 , sizeof(inDegree) );
// memset( ans, 0, sizeof(ans) );
}
bool run ( ) {
int cntOfZeroDegree = 0;
// cntOfVertex = 0;
priority_queue<int, vector<int>, greater<int> >q; //当要求编号小的优先输出时用优先队列存储点
while ( !q.empty() ) q.pop();
for ( int i = st; i < ed+1; ++i )
if ( !inDegree[i] )
q.push( i );
while ( !q.empty() ) {
int u = q.top();
q.pop();
cntOfZeroDegree++;
// ans[cntOfVertex++] = u;
for ( int v = st ; v < ed+1 ; ++v ) {
if ( graph[u][v] ) {
inDegree[v]-- , graph[u][v] = 0 ;
if ( !inDegree[v] )
q.push( v ) ;
}
}
}
return cntOfZeroDegree!=(ed-st+1); // 真为有环
}
}tp;