简体   繁体   English

如何在Java中实现动态数组堆栈?

[英]How can I implement a Dynamic Array Stack in Java?

I need to modify a class to create a dynamic array stack. 我需要修改一个类来创建一个动态数组栈。 My code at this point looks something like this: 我的代码在这一点看起来像这样:

public class DynamicArrayStack<E> implements Stack<E> {                                                                                                                                                                                                                                                                                                                                      

  private E[] elems;  //used to store the elements
  public static final int defaultIncrement = 25;
  private final int increment;

  private int top;  

  @SuppressWarnings( "unchecked" )  
  public DynamicArrayStack( int increment ) {
     this.increment = increment;

     elems = (E[]) new Object[ increment ];
     top = 0;

  }


  /** 
   * Constructor with no parameter that will initialize
   * the stack to have an array whose size is the value
   * of increment and memorise that value as the value
   * of increment.
   */  
  public void ArraySize() { }

  public boolean isEmpty() {
      return top == 0;
  }  

  public E peek() {
      return elems[ top-1 ];
  }  

  public E pop() {
      // save the top element
      E saved = elems[ --top ];
      // scrub the memory, then decrements top
      elems[ top ] = null;
      return saved;
  }  

  public void push( E elem ) {
      // stores the element at position top, then increments top
      elems[ top++ ] = elem;
  }  

  public String toString() {

      StringBuffer b;
      b = new StringBuffer( "DynamicArrayStack: {" );

      for ( int i=top-1; i>=0; i-- ) {
          if ( i!=top-1 ) {
              b.append( "," );
          }
          b.append( elems[ i ] );
      }

      b.append( "}" );

      return b.toString();
  }  
}

How do I edit the first constructor to set increment as the initial size of the stack and that same value to be used when increasing or decreasing the size of the array. 如何编辑第一个构造函数以将增量设置为堆栈的初始大小,以及在增大或减小数组大小时使用的相同值。 My method for doing this seems way too simple. 我这样做的方法似乎太简单了。 Parameter must be > 0 and a fixed number of cells are added or removed when the size of the array changes. 当数组大小发生变化时,参数必须> 0并且添加或删除固定数量的单元格。

The second constructor should set the stack to have an array whose size is the value of increment. 第二个构造函数应该将堆栈设置为一个数组,其大小为increment的值。 I keep getting errors here because I can't figure out how to do that because I thought that was already set in the first constructor. 我一直在这里得到错误,因为我无法弄清楚如何做到这一点因为我认为这已经在第一个构造函数中设置了。 Also the size of the array as the value of increment. 数组的大小也作为增量值。

Also how do I make this class capable of changing the capacity of the stack and into which method should I place that code? 另外,我如何使这个类能够改变堆栈的容量以及我应该将该代码置于哪种方法?

Here is the simple java code to implement it: 这是实现它的简单 java代码

1)Stack based: 1)基于堆栈:

  public class DynamicArrayStack {
    public static void main(String[] args) {

        DynamicStack dstack=new DynamicStack(2);
        System.out.println("--Pushing--");
        dstack.push(1);
        dstack.push(2);
        dstack.display();
        dstack.push(3);
        dstack.push(2);
        dstack.push(5);
        dstack.display();
        System.out.println("--Popping--");
        dstack.pop();
        dstack.pop();
        dstack.pop();
        dstack.display();

    }

}

class DynamicStack {
    private int top;
    private int capacity;
    private int[] array;

    public DynamicStack(int cap) {
        capacity = cap;
        array = new int[capacity];
        top = -1;
    }

    public void push(int data) {
        if (isFull()){
            expandArray();      //if array is full then increase its capacity
        }
        array[++top] = data;    //insert the data
    }

    public void expandArray() {
        int curr_size = top + 1;
        int[] new_array = new int[curr_size * 2];
        for(int i=0;i<curr_size;i++){
            new_array[i] = array[i];
        }
        array = new_array;              //refer to the new array 
        capacity = new_array.length;
    }

    public boolean isFull() {
        if (capacity == top+1)
            return true;
        else
            return false;
    }

    public int pop() {
        if (isEmpty()) {
            System.out.println("Stack is empty");
            return -1;
        } else {
            reduceSize();                 //function to check if size can be reduced
            return array[top--];
        }
    }

    public void reduceSize() {
        int curr_length = top+1;
        if (curr_length < capacity / 2) {
            int[] new_array = new int[capacity / 2];
            System.arraycopy(array, 0, new_array, 0, new_array.length);
            array = new_array;
            capacity = new_array.length;
        }
    }

    public boolean isEmpty() {
        if (top == -1)
            return true;
        else
            return false;
    }

    public void display() {
        for (int i = 0; i <= top; i++) {
            System.out.print(array[i] + "=>");
        }
        System.out.println();
        System.out.println("ARRAY SIZE:" + array.length);
    }

}

OUTPUT: OUTPUT:

--Pushing-- - 推动 -

1=>2=> 1 => 2 =>

ARRAY SIZE:2 ARRAY SIZE:2

1=>2=>3=>2=>5=> 1 => 2 => 3 => 2 => 5 =>

ARRAY SIZE:8 ARRAY SIZE:8

--Popping-- --Popping--

1=>2=> 1 => 2 =>

ARRAY SIZE:4 ARRAY SIZE:4

2)Link List based: 2)基于链接列表:

   public class LinkListStack {
    public static void main(String[] args) {

        StackList stack = new StackList();
        System.out.println("--Pushing--");
        stack.push(1);
        stack.push(2);
        stack.push(3);
        stack.push(4);
        stack.push(5);
        stack.push(6);
        stack.display();
        System.out.println("--Popping--");
        stack.pop();
        stack.pop();
        stack.display();

    }
}

class Node {
    private int data;
    private Node next;

    public Node(int d) {
        data = d;
        next = null;
    }

    public int getData() {
        return data;
    }

    public void setData(int data) {
        this.data = data;
    }

    public Node getNext() {
        return next;
    }

    public void setNext(Node next) {
        this.next = next;
    }

}

class StackList {
    private Node top;
    private int length;

    public StackList() {
        length = 0;
        top = null;
    }

    public void push(int data) {
        Node temp = new Node(data);
        if (top == null) {
            top = temp;
        } else {
            temp.setNext(top);
            top = temp;
        }
        length++;
    }

    public int pop() {
        Node temp=top;
        int data = top.getData();
        top = top.getNext();
        temp=null;
        length--;
        return data;
    }

    public void display() {
        Node temp = top;
        if (isEmpty()) {
            System.out.println("Stack is empty");
        } else {
            while (temp != null) {
                System.out.print(temp.getData() + "=>");
                temp = temp.getNext();
            }
        }
        System.out.println();
    }

    public boolean isEmpty() {
        return (top == null);
    }

}

OUTPUT: OUTPUT:

--Pushing-- - 推动 -

6=>5=>4=>3=>2=>1=> 6 => 5 => 4 => 3 => 2 => 1 =>

--Popping-- --Popping--

4=>3=>2=>1=> 4 => 3 => 2 => 1 =>

Default constructor 默认构造函数

Your default constructor could simply call your other constructor with a default increment value. 您的默认构造函数可以使用默认增量值调用其他构造函数。 For example: 例如:

public DynamicArrayStack() {
    this(defaultIncrement);
}

Expanding the array 扩展阵列

The correct place to expand the array is within the push method. 扩展数组的正确位置在push方法中。 When attempting to add a new element you can check if the array is large enough, and if not create a new larger array. 尝试添加新元素时,可以检查数组是否足够大,如果没有,则创建一个新的更大的数组。 For example you could do the following: 例如,您可以执行以下操作:

@Override
public E push(final E elem) {
    // Check if we need to expand the array
    if (elems.length - 1 == top) {
        @SuppressWarnings("unchecked")
        final E[] newElems = (E[]) new Object[elems.length + increment];
        System.arraycopy(elems, 0, newElems, 0, elems.length);
        elems = newElems;
    }
    // stores the element at position top, then increments top
    elems[top++] = elem;
    return elem;
}

If you want to shrink the array the sensible place to do this would be in the pop() method. 如果你想缩小数组,那么合理的地方就是pop()方法。 You might want to consider only reducing the length when (top + (increment*2))<elems.length to avoid repeatedly copying arrays when you're on the boundary. 您可能只想考虑减少(top + (increment*2))<elems.length时的长度,以避免在边界上重复复制数组。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM