以下代码中使用了哪个ADT,您将如何得出这个结论?我有一种预感,认为它是一个循环链表,但没有确切的推理为什么。
public class Josephus {
private final int M = 3;
private class Soldier {
int num;
Soldier next;
Soldier(int n) {
num = n;
}
}
public void survivor(int N) {
System.out.println("Number of soldiers = " + N);
if (N <= 0)
return;
Soldier first = new Soldier(0);
Soldier curr = first;
for (int i =1; n<N; i++) {
curr.next = new Soldier(i);
curr = curr.next;
}
curr.next = first;
Soldier prev = curr;
int d = 0;
int m = 0;
while (curr != prev) {
if(++m >= M){
d++;
System.out.println("Dead soldier = " + curr.num);
if (curr.num == 0) {
System.out.println("You died as number = " + d);
}
prev.next = curr.next;
m = 0;
} else
prev = curr;
curr = curr.next;
}
System.out.println("Final survivor is = " + curr.num);
}
}
答案 0 :(得分:3)
我不是数据结构专家,但我相信你的循环链表直觉是正确的。首先,我注意到代码的以下部分代表了数据结构的典型“节点”:
private class Soldier {
int num;
Soldier next;
Soldier(int n) {
num = n;
}
}
在这里我们可以看到Soldier next;
是对下一个节点的引用。当你看到一个由自己的对象组成的类时,通常会有一个死亡的赠品。现在,没有“前一个”字段或“左/右子”字段。这表明我们不处理二叉树,双链表或任何这种性质的东西。其中留下单链表或循环链表。
这是构建链表的地方:
Soldier first = new Soldier(0);
Soldier curr = first;
for (int i =1; n<N; i++) {
curr.next = new Soldier(i);
curr = curr.next;
}
我们可以看到for循环的每次迭代都会创建一个new Soldier
对象,然后将节点的引用从上一次迭代中分配给这个新的Soldier:
curr.next = new Soldier(i);
接下来,我们将新构造的Soldier
对象分配给curr
,以便在下一次迭代中我们可以指向列表中的下一个节点:
curr = curr.next;
在循环结束时,我们最终将最终节点指向null。如果没有解决这个问题,那么我们会有一个单独的链表。然而,这并非如我们在紧接其后的行中所见:
curr.next = first;
以下是最后添加的节点的引用被分配给列表中的第一个节点(在此处初始化:Soldier first = new Soldier(0);
),从而使列表成为循环。
其余代码似乎只是在列表上进行迭代,并且对数据结构本身没有影响。对不起,如果我说了一些非常明显的事情,我只想彻底:)
答案 1 :(得分:1)
这是数据结构是循环Linked Lists
答案 2 :(得分:1)
这里的问题可以很好地了解所使用的数据结构。约瑟夫斯问题基本上是一个游戏,其中士兵站成一个圆圈,每个第k个人被消灭,直到只剩下一名士兵。现在我们需要模拟站在一个圆圈中的士兵列表,因此适当的假设是使用的数据结构是一个循环链接列表。