两种双向链表的首项插入与删除效率比较
来源:互联网 发布:java socket 百度云盘 编辑:程序博客网 时间:2024/06/10 06:34
这里说的两种双向链表是指带“sentinel”与不带“sentinel”的,其中带"sentinel"的多了一个"sentinel"节点,以空间换取了时间。两种链表如下图:
1.不带sentinel的:
下面是构造方法以及在首项插入和删除方法,从代码中可以看出没有sentinel的DList在插入时需要处理链表为空的情况,删除的时候需要处理链表为空以及链表只有一个元素的情况,比较麻烦。
public class DList1 { /** * head references the first node. * tail references the last node. */ protected DListNode1 head; protected DListNode1 tail; protected long size; /* DList1 invariants: * 1) head.prev == null. * 2) tail.next == null. * 3) For any DListNode1 x in a DList, if x.next == y and x.next != null, * then y.prev == x. * 4) For any DListNode1 x in a DList, if x.prev == y and x.prev != null, * then y.next == x. * 5) The tail can be accessed from the head by a sequence of "next" * references. * 6) size is the number of DListNode1s that can be accessed from the * head by a sequence of "next" references. */ /** * DList1() constructor for an empty DList1. */ public DList1() { head = null; tail = null; size = 0; } /** * DList1() constructor for a one-node DList1. */ public DList1(int a) { head = new DListNode1(); tail = head; head.item = a; size = 1; } /** * DList1() constructor for a two-node DList1. */ public DList1(int a, int b) { head = new DListNode1(); head.item = a; tail = new DListNode1(); tail.item = b; head.next = tail; tail.prev = head; size = 2; } /** * insertFront() inserts an item at the front of a DList1. */ public void insertFront(int i) { DListNode1 insertItem = new DListNode1(i); if(head == null){ head = insertItem; tail = insertItem; }else{ insertItem.next = head; head.prev = insertItem; head = insertItem; } size++; } /** * removeFront() removes the first item (and node) from a DList1. If the * list is empty, do nothing. */ public void removeFront() { if(size == 0){ return; } if(size == 1){ head = null; tail = null; }else{ head.next.prev = null; head = head.next; } size--; }
下边是构造方法以及首先插入与删除方法,注意构造方法中head的prev和next在链表没有元素的情况下是指向自身的,这一点非常重要,如果设置为null,就失去了这种链表的优势,还需要像第一种链表一样在插入和删除的时候考虑多种情况。
public class DList2 { /** * head references the sentinel node. * */ protected DListNode2 head; protected long size; /* DList2 invariants: * 1) head != null. * 2) For any DListNode2 x in a DList2, x.next != null. * 3) For any DListNode2 x in a DList2, x.prev != null. * 4) For any DListNode2 x in a DList2, if x.next == y, then y.prev == x. * 5) For any DListNode2 x in a DList2, if x.prev == y, then y.next == x. * 6) size is the number of DListNode2s, NOT COUNTING the sentinel * (denoted by "head"), that can be accessed from the sentinel by * a sequence of "next" references. */ /** * DList2() constructor for an empty DList2. */ public DList2() { head = new DListNode2(); head.item = Integer.MIN_VALUE; head.next = head; head.prev = head; size = 0; } /** * DList2() constructor for a one-node DList2. */ public DList2(int a) { head = new DListNode2(); head.item = Integer.MIN_VALUE; head.next = new DListNode2(); head.next.item = a; head.prev = head.next; head.next.prev = head; head.prev.next = head; size = 1; } /** * DList2() constructor for a two-node DList2. */ public DList2(int a, int b) { head = new DListNode2(); head.item = Integer.MIN_VALUE; head.next = new DListNode2(); head.next.item = a; head.prev = new DListNode2(); head.prev.item = b; head.next.prev = head; head.next.next = head.prev; head.prev.next = head; head.prev.prev = head.next; size = 2; } /** * insertFront() inserts an item at the front of a DList2. */ public void insertFront(int i) { DListNode2 insertItem = new DListNode2(i); head.next.prev = insertItem; insertItem.next = head.next; insertItem.prev = head; head.next = insertItem; size++; } /** * removeFront() removes the first item (and first non-sentinel node) from * a DList2. If the list is empty, do nothing. */ public void removeFront() { if(size == 0){ return; } DListNode2 remove = head.next; head.next = remove.next; remove.next.prev = head; size--; }
0 0
- 两种双向链表的首项插入与删除效率比较
- 双向链表的插入与删除
- 双向链表的插入与删除
- list与vector的尾部插入删除效率比较
- 双向循环链表的创建,插入与删除。
- 双向链表的建立插入与删除
- 双向链表的插入与删除节点
- 双向链表插入与删除
- 双向链表插入与删除
- 双向循环链表的插入删除
- 双向链表的建立插入删除
- 双向链表的创建/插入/删除
- 双向链表的插入删除操
- 双向链表的生成,删除,插入
- 双向链表的插入以及删除
- 双向链表的插入、删除、遍历
- 双向链表的插入和删除
- 双向链表插入删除
- go语言的IDE实现自动补全的功能
- IOS学习 非ARC工程转ARC工程以及其内部对应(比较详细的记录的主要问题)
- Android OpenGL ES 开发教程 从入门到精通
- Longge's problem 隐含了错误 WA
- 电机电流导致cereal_port异常调试
- 两种双向链表的首项插入与删除效率比较
- cygwin编C程序,去除cygwin属性
- 实现单文件上传,页面局部刷新
- 深入分析redis持久化(转)
- 现在网络中html保存到文件也可以保存图片
- 初学MongoDB实践笔记——安装、创建数据库、保存及查询数据
- Java多线程编程(一)-多线程编程设计要点
- WinDbg Command 窗口不显示解决方法
- Spring--quartz中cronExpression配置说明