栈的定义
- 栈(stack)是限制插入和删除只能在一个位置上进行的表,该位置是表的末端,叫做栈顶(top),有的称为限定性的限制表结构。栈有时也叫做 LIFO (后进先出)表。
数组实现栈
- 使用数组实现栈
优点:一个元素占用一个存储空间;
缺点:如果初始化申请的存储空间太大,浪费存储空间。如果申请的存储空间太小,如果后期需要扩充空间,扩充是一个费时的操作,这样会造成性能的下降。
-
时间复杂度为 O(1)
-
代码如下:
/**
* 数组方式实现栈
*/
public class MyStack<T> {
// 定义数组存放数据
private ArrayList<T> arr;
// 定义栈的大小
private int stackSize;
public MyStack() {
arr = new ArrayList<>();
stackSize = 0;
}
/**
* 判断是否是null
*/
boolean isEmpty() {
return stackSize == 0;
}
/**
* 获取栈大小
*/
int size() {
return stackSize;
}
/**
* 获取栈顶元素
*/
T top() {
if (isEmpty()) {
return null;
}
return arr.get(stackSize - 1);
}
/**
* 弹栈
*/
T pop() {
if (stackSize > 0) {
return arr.get(--stackSize);
} else {
System.out.println("栈为null");
return null;
}
}
/**
* 压栈
*/
void push(T item){
stackSize++;
arr.add(item);
}
}
- 调用如下:
@Test
public void test() {
MyStack<Integer> myStack = new MyStack<>();
myStack.push(1);
myStack.push(2);
myStack.push(3);
System.out.println("栈顶元素为:" + myStack.top());
System.out.println("栈大小为:" + myStack.size());
myStack.pop();
System.out.println("弹栈成功");
System.out.println("栈大小为:" + myStack.size());
System.out.println("栈顶元素为:" + myStack.top());
}
链表实现栈
- 优缺点
优点:使用灵活方便,只有在需要的时候才申请存储空间。
缺点:除了要存储元素外,还要额外的存储指针信息。
-
时间复杂度为 O(1)
-
栈实现如下:
/**
* 链表方式实现栈
*/
public class MyStack2<T> {
static class LNode<T> {
T data;
LNode<T> next;
}
private LNode<T> head;
public MyStack2() {
head = new LNode<T>();
head.data = null;
head.next = null;
}
/**
* 栈是否为null
*/
boolean empty() {
return head == null;
}
/**
* 大小
*/
int size() {
int size = 0;
LNode<T> node = head.next;
while (node != null) {
node = node.next;
size++;
}
return size;
}
T top() {
if (head == null || head.next == null) {
return null;
}
return head.next.data;
}
T pop() {
LNode<T> tmp = head.next;
if (tmp != null) {
head.next = tmp.next;
return tmp.data;
}
System.out.println("栈为null");
return null;
}
void push(T item) {
LNode<T> addItem = new LNode<>();
addItem.data = item;
addItem.next = head.next;
head.next = addItem;
}
}
- 调用如下:
@Test
public void test2() {
MyStack2<Integer> myStack = new MyStack2<>();
myStack.push(1);
myStack.push(2);
myStack.push(3);
System.out.println("栈顶元素为:" + myStack.top());
System.out.println("栈大小为:" + myStack.size());
myStack.pop();
System.out.println("弹栈成功");
System.out.println("栈大小为:" + myStack.size());
System.out.println("栈顶元素为:" + myStack.top());
}