一. 循环单链表
1.如何建立一个循环单链表类
要用到内部类,整个链表是一个类,内部类为链表的Entry节点。
class TestClink{
private Entry head = null;
class Entry{//节点类
int data;
Entry next;
public Entry(){//头结点的构造函数
this.data = -1;
next = null;
}
public Entry(int data){//带参构造函数
this.data = data;
next = null;
}
}
public TestClink(){//头结点的初始化
this.head = new Entry();
this.head.next = this.head;//让自己指向自己
}
2. 头插法
public void insertHead(int val){
Entry cur1 = new Entry(val);
cur1.next = this.head.next;//先保后面的节点
this.head.next = cur1;
}
3.尾插法
public void insertTail(int val){
Entry entry = new Entry(val);
Entry cur = this.head;
while(cur.next != head){//遍历循环链表
cur = cur.next;
}
entry.next = cur.next;
cur.next = entry;
}
4.删除所有值为k的节点
public void delete(int k){
Entry cur1 = head.next;
Entry cur2 = head;//前驱
while(cur1 != head){
if(cur1.data == k){
cur2.next = cur1.next;//让前驱指向当前节点的下一个
cur1 = cur2.next;
}else{
cur1 = cur1.next;
cur2 = cur2.next;
}
}
}
5.获取循环单链表的长度
public int getLength(){
int t = 0;
Entry cur = head.next;
while(cur != head){
t++;
cur = cur.next;
}
return t;
}
二. 双向链表
需要在节点域里多增加一个前驱指针prio
class TestDlink{
private Entry head = null;
class Entry{
int data;
Entry next;
Entry prio;
public Entry(){
this.data = -1;
this.next = null;
this.prio = null;
}
public Entry(int val){
this.data = val;
this.next = null;
this.prio = null;
}
}
双向链表的构造函数
public TestDlink(){
this.head = new Entry();
}
1. 头插法
public void insertHead(int val){
Entry entry = new Entry(val);
entry.next = this.head.next;
entry.prio = head;
head.next = entry;
if(entry.next != null){
entry.next.prio = entry;
}
}
在进行头插法时一定要注意,插入节点为链表的第一个节点的话,此时head的next域为空,不可以将entry的next的前驱指向entry,因此在写这一句
entry.next.prio = entry;
时,要加上一个条件判断,entry的next是否为空,不为空才可以将它下一个节点的prio指向entry。
3. 尾插法
public void insertTail(int val){
Entry cur = head;
Entry entry = new Entry(val);
while(cur.next != null){//遍历
cur = cur.next;
}
cur.next = entry;
entry.prio = cur;
}
4.删除双向链表的k这个元素
public void delete(int val){
Entry cur = this.head.next;
while(cur != null){
if(cur.data == val){
cur.prio.next = cur.next;
if(cur.next != null){//只有cur的next不为空时,它的next才会有前驱
cur.next.prio = cur.prio;
}
cur = cur.next;
}else{
cur = cur.next;
}
}
}
三. 顺序栈
栈是一种先进后出的数据结构,顺序栈用数组来实现
class Stack{
int top;//栈顶指针
int[] elem;
public Stack(){
this(10);
}
public Stack(int size){
this.elem = new int[size];
this.top = 0;
}
}
1. 判断栈空
public boolean isEmpty(){
if(this.top == 0){//栈顶指针为0
return true;
}
return false;
}
2. 判断栈满
public boolean isFull(){
if(this.top == this.elem.length){//栈顶指针等于数组长度
return true;
}
return false;
}
3.入栈
public boolean push(int n){
if(isFull()){//入栈之前判断栈满
return false;
}
this.elem[this.top++] = n;
return true;
}
也可以这样写
this.elem[this.top] = n;
top++;
4. 出栈
public boolean pop(){
if(isEmpty()){
return false;
}
--this.top;
return true;
}
5.得到栈顶元素
public int getpop(){
if(isEmpty()){//判断栈空
return -1;
}
return elem[this.top - 1];
}
不要将 this.top - 1写成 --this.top,因为函数的作用是得到栈顶元素,并非出栈。