1.栈的链式存储结构定义。
- 栈只是栈顶来做插入和删除操作,那么链表的栈顶应该放在链表的头部还是尾部呢。由于链表存在头指针,栈存在栈顶指针,那么便让它们指向一个位置更加方向操作和理解,所以将栈顶放在单链表的头部。也因如此,单链表的头结点也没有意义了。所以对于栈的链式存储来说,不需要头结点。
- 同时,栈的链式存储基本不存在栈满的情况,主要看系统的内存。
- 栈元素的进出特点是先进后出。
- 因为链表存在头结点指针,头结点指针指向空。栈的链式存储存在栈顶指针,所以将栈顶指针同样指向空。
- 栈的链式实现的接口是Stack。
2.LinkedStack的定义。
+Linkedlist list //队列的链式由线性表的链式实现,创建一个LinkedList<E>类型的变量list
+LinkedStack() //构造函数的搭建
+String toString() //toString的方法函数
+boolean equals(Object obj) //equals的方法函数
栈链式的构建是由链式的线性表实现的,在这里和栈的顺序存储有异曲同工之意,可以对照1线性表的顺序存储和2栈的顺序存储加1线性表的链式存储结合观看琢磨。
①进栈图解。
元素进栈就是在线性表的链式队头加入元素,每次加入元素后,老元素往后移动堆积。
②出栈图解。
元素的出栈就是在队头位置的元素出栈,先进栈的老元素仍然在后边。
3.栈的链式的toString()方法。
1、使用线程不安全的StringBuilder类创建对象sb。
2、对栈链判断是否为空,为空直接返回sb.append("[ ]");。
3、不为空则先连接sb.append("[");。
4、之后使用获得元素方法,使用for循环,将元素开始连接,每连接一次,只要未到达最后一个元素,那么后边连接逗号sb.append(',');,当到达最后一个元素后,在最后连接的元素后边连接上sb.append(']');。
@Override
public String toString() {
StringBuilder sb=new StringBuilder(); //1
sb.append("LinkedStack:size="+getSize()+"\n");
if(isEmpty()){ //2
sb.append("[]");
}else{
sb.append("["); //3
for(int i=0;i<getSize();i++){ //4
sb.append(list.get(i));
if(i!=getSize()-1){
sb.append(',');
}else{
sb.append(']');
}
}
}
return sb.toString();
}
4.栈的链式的equals(Object obj)方法。
1、先对传入的对象obj判断是否为空,为空则返回false。
2、再对该对象obj与this直接判断是否相等,相等直接返回true。
3、最后比较里边内容,将obj强转成LinkedStack<E>即可开始。
4、返回 return this.list.equals(l.list);。
public boolean equals(Object obj){
if(obj==null){
return false;
}
if(obj==this){
return true;
}
if(obj instanceof LinkedStack){
LinkedStack<E> l=(LinkedStack<E>) obj;
return this.list.equals(l.list);
}
return false;
}
5.栈的链式的全部代码实现。
package com.oupeng.p5链表;
import com.oupeng.p2栈.Stack;
public class LinkedStack<E> implements Stack<E> {
private LinkedList<E> list; //栈的链式由线性表的链式实现,创建一个LinkedList<E>的变量list
public LinkedStack() { //构造函数的搭建
list=new LinkedList<E>();
}
@Override
public int getSize() { //栈链式获取元素总和
return list.getSize(); //也就是线性表链式的元素总和,返回
}
@Override
public boolean isEmpty() { //栈链式判断是否为空
return list.isEmpty(); //也就是线性表链式是否为空
}
@Override
public void push(E e) { //栈链式的元素进出是先进后出
list.addFirst(e); //也就是线性表链式的头结点下一跳的插入元素e
}
@Override
public E pop() { //栈链式的元素进出是先进后出
return list.removeFirst();//也就是线性表链式的头结点下一跳数据data删除
}
@Override
public E peek() { //栈链式栈顶元素的获取
return list.getFirst(); //也就是线性表链式的头结点的下一跳数据data的获取
}
@Override
public void clear() { //栈链式的清空
list.clear(); //也就是线性表的清空
}
@Override
public String toString() {
StringBuilder sb=new StringBuilder();
sb.append("LinkedStack:size="+getSize()+"\n");
if(isEmpty()){
sb.append("[]");
}else{
sb.append("[");
for(int i=0;i<getSize();i++){
sb.append(list.get(i));
if(i!=getSize()-1){
sb.append(',');
}else{
sb.append(']');
}
}
}
return sb.toString();
}
public boolean equals(Object obj){
if(obj==null){
return false;
}
if(obj==this){
return true;
}
if(obj instanceof LinkedStack){
LinkedStack<E> l=(LinkedStack<E>) obj;
return this.list.equals(l.list);
}
return false;
}
}