import java.util.Iterator; import java.util.Random; public class Main { public static void main(String[] args) { Random rand = new Random(1); Stack stack = Math.random() < 0.5 ? new AStack() : new RStack(); System.out.println(stack); for (int i = 0; i < 10; ++i) { int n = rand.nextInt(10); stack.push(n); System.out.print(n + ": "); for (Integer j : stack) { System.out.print(j + " "); } System.out.println(); } Integer n; while((n = stack.pop()) != null) { System.out.print(n + ": "); for (Integer j : stack) { System.out.print(j + " "); } System.out.println(); } } } interface Stack extends Iterable { E pop(); void push(E data); } class AStack implements Stack { private class StackIterator implements Iterator { public boolean hasNext() { return curr > 0; } public E next() { return (E)stack[--curr]; } public void remove() { throw new UnsupportedOperationException(); } private int curr = top; } private void grow() { Object[] temp = new Object[stack.length * 2]; for (int i = 0; i < stack.length; ++i) { temp[i] = stack[i]; } stack = temp; } public Iterator iterator() { return new StackIterator(); } public E pop() { E temp = null; if (top > 0) { temp = (E)stack[--top]; } if (stack.length > 10 && top <= stack.length / 3) { shrink(); } return temp; } public void push(E data) { if (top >= stack.length) { grow(); } stack[top++] = data; } private void shrink() { Object[] temp = new Object[stack.length / 2]; for (int i = 0; i < top; ++i) { temp[i] = stack[i]; } stack = temp; } private Object[] stack = new Object[10]; private int top; } class RStack implements Stack { private class Node { private Node(T data) { this.data = data; } private T data; private Node next; } public Iterator iterator() { return new Iterator() { public boolean hasNext() { return curr != null; } public E next() { E temp = curr.data; curr = curr.next; return temp; } public void remove() { throw new UnsupportedOperationException(); } Node curr = head; }; } public E pop() { E temp = null; if (head != null) { temp = head.data; head = head.next; } return temp; } public void push(E data) { Node temp = new Node(data); temp.next = head; head = temp; } private Node head; }