考察知识点: 拓扑排序、队列
题目分析:
做一件事之前必须先完成一些事,这样的做事顺序就是拓扑序列。可以使用队列判断一个序列能否是拓扑序。
首先如果做一件事之前不需要做其他事,那么我们就可以选择完成这一件事。当这一件事完成之后,可能就会有依赖这件事的事情可以做了。对该题而言,首先记录每个节点被哪些结点依赖,然后记录每一个结点的入度。
记录完所有的事件后,遍历所有事件的入度,如果为0那么我们就将其加入到队列中。完成后对队列中的元素进行访问,每次访问完毕后将结点加入到vector中并释放该节点,那么依赖该结点的事件就有可能入度为0了。将入度为0的序列加入到队列中等待被重复上述处理即可。
当队列中处理完毕后,如果访问到的牛的数量小于给出的牛的数量,说明在处理过程中产生了环,使得该环中的所有牛的入度都不为0,返回空vector即可;否则返回包含答案的vector即可。
所用编程语言: C++
class Solution { public: /** * 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可 * * * @param numCows int整型 * @param feedOrders int整型vector<vector<>> * @return int整型vector */ vector<int> findFeedOrderII(int numCows, vector<vector<int> >& feedOrders) { // write code here vector<vector<int>> next(numCows); vector<int> indegree(numCows); queue<int> zeroq; vector<int> res; for (auto &feedOrder: feedOrders) { int ai = feedOrder[0]; int bi = feedOrder[1]; next[bi].push_back(ai); indegree[ai]++; } for (int i = 0 ; i < numCows; i++) { if (indegree[i] == 0) zeroq.push(i); } while (!zeroq.empty()) { int cow = zeroq.front(); zeroq.pop(); numCows--; res.push_back(cow); for (auto &nextCow: next[cow]) { if (--indegree[nextCow] == 0) zeroq.push(nextCow); } } if (!numCows) return res; else return {}; } };