我的作业问题提供了一些课程,有多少课程相互依赖。例如,第一个测试(课程,取决于):(1,3)(2,3)(4,1)(4,2),我们确定有5个课程和4个相互依赖(即为什么5不在列表中,它只是0)
从拓扑搜索中我知道,以下是有效的解决方案: 1 3 2 4 0
然后我需要打印出这些课程的学期数,由于它们之间的关系,我知道这是3个学期。首先,我们必须选择课程1和2才能达到3,并且由于我们已经拥有1,所以我们可以选择课程4。
所以我需要帮助弄清楚执行此操作的一些代码。那是我需要你们帮助的地方
我试图简单地计算已连接但失败的课程。我尝试过考虑可以做的事情,但实际上没有任何解决方法。
图形类:
public class Graph {
int V;
LinkedList<Integer> adjList[];
public Graph(int vertex) {
this.V = vertex;
//We then define the num of vertexes in the adjlist
adjList = new LinkedList[vertex];
//Then create a new list for each vertex so we can create a link between the vertexes
for (int i = 0; i < vertex; i++) {
adjList[i] = new LinkedList<>();
}
}
//Directed graph
public void addEdge(int source, int destination) {
//Add the edge from the source node to the destination node
adjList[source].add(destination);
adjList[destination].add(source);
}
//Method to print the graph if necessary
public void printGraph(Graph graph) {
for (int i = 0; i < graph.V; i++) {
System.out.println("Adjacency list over vertex: " + i);
System.out.print("head");
for (Integer treeCrawler : graph.adjList[i]) {
System.out.print("-> " + treeCrawler);
}
System.out.println("\n");
}
}
public LinkedList<Integer>[] getAdjList() {
return adjList;
}
}
和拓扑排序类,我们用于解决问题的算法
public class TopologicalSort {
int vertex;
//This function helps the topological function recursively by marking the vertices and pushing them onto the stack
public void topologicalHelper(int vertex, boolean marked[], Stack nodes, Graph graph) {
List<Integer>[] list = graph.getAdjList();
marked[vertex] = true;
Iterator<Integer> iterator = list[vertex].iterator();
while (iterator.hasNext()) {
int temp = iterator.next();
if (!marked[temp] && list[temp].size() != 0) {
topologicalHelper(temp, marked, nodes, graph);
}
}
nodes.add(vertex);
}
public TopologicalSort(Graph graph, int vertecies) {
vertex = vertecies;
Stack nodes = new Stack();
boolean[] marked = new boolean[vertex];
for (int i = 0; i < vertex; i++) {
if (marked[i] == false) {
topologicalHelper(i, marked, nodes, graph);
}
}
while(!nodes.empty()) {
System.out.print(nodes.pop() + " ");
}
}
}
结果应该为3,但是我尚未在所有解决方案构想中得出该数字,我需要一些帮助或提示。
哦,下面是控制台输出
Adjacency list over vertex: 0
head
Adjacency list over vertex: 1
head-> 3-> 4
Adjacency list over vertex: 2
head-> 3-> 4
Adjacency list over vertex: 3
head-> 1-> 2
Adjacency list over vertex: 4
head-> 1-> 2
1 3 2 4 0
答案 0 :(得分:0)
依赖关系是有向属性,因此您应该使用有向图。填充图形后,u最终将出现一个断开的图形,其中包含一棵或多棵树。找出哪些节点是每棵树的根,然后使用DFS获取每棵树的最大深度。假设每学期没有课程限制,那么所有树木的最大深度就是解决方案。
public class Graph {
int V;
ArrayList<Integer> adjList[];
boolean[] notRoot;
public Graph(int vertex) {
this.V = vertex;
adjList = new ArrayList[vertex];
notRoot = new boolean[vertex];
for (int i = 0; i < vertex; i++) {
adjList[i] = new ArrayList<Integer>();
}
}
public void addEdge(int a, int b) {
//asuming b is dependent on a
adjList[b].add(a);
notRoot[a]=true;
}
int maxDepthDfs(int root){
int depth=1;
for(int i=0;i<adjList[root].size();i++){
int child=adjList[root].get(i);
depth=Math.max(maxDepthDfs(child)+1,depth);
}
return depth;
}
public int getSolution(){
int ans=0;
for(int i=0;i<V;i++){
if(!notRoot[i])
ans=Math.max(ans,maxDepthDfs(i));
}
return ans;
}
}
一种拓扑排序就是将节点添加到堆栈中的DFS(先添加节点的所有子节点,然后再添加根节点)。在Kahn的算法中,首先找到根元素(没有父节点的节点),然后仅调用该方法或那些节点。
int maxDepthDfs(int root){
//since we are only calling this function for root nodes we need not check if nodes were previously visited
int depth=1;
for(int i=0;i<adjList[root].size();i++){
int child=adjList[root].get(i);
depth=Math.max(maxDepthDfs(child)+1,depth);
}
s.push(root);
return depth;
}
public int getSolution(){
s=new Stack<Integer>();
int ans=0;
for(int i=0;i<V;i++){
if(!notRoot[i])
ans=Math.max(ans,maxDepthDfs(i));
}
//stack s contains result of topological sort;
return ans;
}