44

今天我试图推入java.util.Stack课堂,然后使用Iterator迭代(不使用弹出)通过项目。我期待 LIFO 财产,但感到惊讶。

这是我正在尝试的代码。

import java.util.*;
import java.util.Stack;

public class Main {
    public static void main(String[] args) {
        RobStack<Integer> rstack = new RobStack<Integer>(); // Correct Implementation
        Stack<Integer> jstack = new Stack<Integer>(); // Default Java Implementation
        rstack.push(0); jstack.push(0);
        rstack.push(1); jstack.push(1);
        rstack.push(2); jstack.push(2);
        rstack.push(3); jstack.push(3);

        System.out.print("Algo Stack: ");
        for (int i : rstack)
            System.out.print(i + " ");
        System.out.print("\nJava Stack: ");
        for (int i : jstack)
            System.out.print(i + " ");
    }

}

上述程序的输出如下:

Algo Stack: 3 2 1 0 
Java Stack: 0 1 2 3 

在上面的代码jstack中使用了默认的 Java 实现,并rstack使用了Robert Sedgewick为他的 Algorithm 类提供的实现。我发现罗伯特教授的实施工作正常,但java.util.Stack实施失败。

这是一个错误还是设计使然

4

7 回答 7

34

请参阅错误 ID 4475301:RFE:java.util.Stack.iterator() 迭代错误的方式。这种行为是(不良)设计的。Java 的内置Stack迭代器方法继承自其他类,因此它们的行为与您期望的不同。

于 2013-06-07T20:58:24.440 回答
13

您应该使用 Deque 而不是 Stack。

Deque<Integer> stack = new ArrayDeque<Integer>();

请参阅 Oracle 文档

于 2014-12-15T19:33:06.207 回答
3

原则上,您不应该遍历 a Stack,而只能从顶部推入或从顶部弹出。至于实际实现,大多数语言,包括 Java,都使用另一种collection type来实现Stack. 从严格要求的角度来看,它应该允许恒定时间push, top and pop运行。

任何附加功能(或本例中的错误)都应该被忽略,而不是依赖于编码。

于 2013-06-07T21:01:30.067 回答
2

也许,您可以使用 .get() 从上到下打印堆栈中的项目。

Stack<Integer> stack = new Stack<Integer>();
stack.push(3);
stack.push(2);
stack.push(1);
// print from top to bottom
for(int i = stack.size() - 1; i >= 0; i--){
   System.out.println(stack.get(i));
}
/*
output
1
2
3
*/
于 2015-07-14T19:19:50.230 回答
1

Eclipse Collections包含一个可变堆栈实现,其中迭代器从上到下返回值。此代码打印 3、2,然后是 1。

MutableStack<Integer> stack = ArrayStack.newStack();
stack.push(1);
stack.push(2);
stack.push(3);
for (Iterator<Integer> iterator = stack.iterator(); iterator.hasNext(); )
{
    Integer each = iterator.next();
    System.out.println(each);
}

MutableStack不扩展MutableCollectionor Collection,例如,您无法从堆栈中间移除。实现内部迭代模式(如forEach()select()collect()anySatisfy()allSatisfy()等)的方法也从上到下处理元素。此代码打印相同的内容。

stack.forEach(Procedures.println(System.out));

注意:我是 Eclipse 集合的提交者。

于 2013-09-03T15:22:09.037 回答
1

Stack从AbstractList继承.listIterator() ,它允许逆序迭代。

Stack<Integer> stack = new Stack<Integer>();
stack.push(1);
stack.push(2);
stack.push(3);
for (ListIterator<Integer> iterator = stack.listIterator(stack.size()); iterator.hasPrevious();) {
    Integer integer = iterator.previous();
    System.out.println(integer);
}
// Output: 3 2 1
于 2014-06-19T09:52:19.170 回答
0

代替 aStack你可以使用 aLinkedList和使用pushandpop方法。

于 2020-09-15T10:28:14.423 回答