首页 > 代码库 > Sicily 1034. Forest

Sicily 1034. Forest

Constraints

Time Limit: 1 secs, Memory Limit: 32 MB

Description

In the field of computer science, forest is important and deeply researched , it is a model for many data structures . Now it’s your job here to calculate the depth and width of given forests.

     Precisely, a forest here is a directed graph with neither loop nor two edges pointing to the same node. Nodes with no edge pointing to are roots, we define that roots are at level 0 . If there’s an edge points from node A to node B , then node B is called a child of node A , and we define that B is at level (k+1) if and only if A is at level k .

      We define the depth of a forest is the maximum level number of all the nodes , the width of a forest is the maximum number of nodes at the same level.

Input

There’re several test cases. For each case, in the first line there are two integer numbers n and m (1≤n≤100, 0≤m≤100, m≤n*n) indicating the number of nodes and edges respectively , then m lines followed , for each line of these m lines there are two integer numbers a and b (1≤a,b≤n)indicating there’s an edge pointing from a to b. Nodes are represented by numbers between 1 and n .n=0 indicates end of input.

Output

For each case output one line of answer , if it’s not a forest , i.e. there’s at least one loop or two edges pointing to the same node, output “INVALID”(without quotation mark), otherwise output the depth and width of the forest, separated by a white space.

Sample Input

1 01 11 13 11 32 21 22 10 88

Sample Output

0 1INVALID1 2INVALID

分析:一看到题目中说到了有环的情况,立马就想到了学数据结构的时候用广搜来进行拓扑排序可以找出环。这道题同样也是用广搜,通过边遍历每一个可以放入森林的节点,每次遍历到一个节点,就删掉指向它的边,要是存在某些边没有被删除,就说明有些节点是非法的。每个节点都有一个level来表示它所在的层数,子节点的层数等于父节点层数加1。

 1 #include <iostream> 2 #include <memory.h> 3 #include <queue> 4 #include <vector> 5 using namespace std; 6  7 struct Node{ 8     int id;                                         //树中每个节点的编号  9     int level;                                      //树中每个节点所在的层数 10 }; 11 12 struct Edge{13     int from;14     int to;15 };16 17 int main(){18     int n, m, i;19     Edge edge;20     Node node;21     Node nodes[100];22     vector<Edge>::iterator iter;23     bool isRoot[100];24     while(cin >> n >> m && n != 0){25         vector<Edge> v;26         queue<Node> q;27         memset(isRoot, true, sizeof(isRoot));28         for(i = 0; i < n; i++){29             nodes[i].id = i + 1;30             nodes[i].level = -1;31         }32         for(i = 0; i < m; i++){33             cin >> edge.from >> edge.to;34             v.push_back(edge);35             isRoot[edge.to - 1] = false; 36         }37         for(i = 0; i < n; i++){38             if(isRoot[i]){39                 node.id = i + 1;40                 node.level = 0;41                 q.push(node);42             }43         }44         /*广搜来标记每个节点的层数*/ 45         while(!q.empty()){46             node = q.front();47             q.pop();48             for(iter = v.begin(); iter != v.end(); iter++){49                 if(iter->from == node.id && nodes[iter->to -1].level == -1){50                     nodes[iter->to -1].level = node.level+1;51                     q.push(nodes[iter->to -1]);52                     v.erase(iter);                  //每次找到一个合法的点就删掉一条边 53                     iter--;54                 }55             }56         }57         if(!v.empty()){                             //有环或者存在几个父节点同时指向一个子节点 58             cout << "INVALID" << endl;59         } else {60             int sum[100];                           //标记每层节点的个数 61             int max = 0;62             memset(sum, 0, sizeof(sum));63             for(i = 0; i < n; i++){64                 if(nodes[i].level == -1){65                     nodes[i].level = 0;66                 }67                 sum[nodes[i].level]++;68             }69             for(i = 0; i < 100; i++){70                 if(sum[i]==0){71                     break;72                 }73                 if(max < sum[i]){74                     max = sum[i];75                 }76             }77             cout << i - 1 << " " << max << endl;78         }79     }80     return 0;81 }                                 

附加测试样例:

输入:4 2
1 2
3 4
输出:1 2

Sicily 1034. Forest