java_linear list
1.线性表的顺序存储结构,类似ArrayList
package collectionsFramework.linearlist; import java.util.Arrays; /** * @Package collectionsFramework.linearlist * @ClassName: Singlylinkedlist * @Description: TODO(arrayList的增删改查) * @author andy * @date 2013-11-21 下午05:39:53 */ public class SinglyLinkedList<T>{ private Object[] elementData; private int size; private int capacity; private int defaultCapacity = 10; private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8; public SinglyLinkedList(){ capacity = defaultCapacity; elementData = new Object[capacity]; } public int getSize() { return size; } public boolean isEmpty(){ return size == 0; } //在线性顺序表的开始处添加一个元素。 public void add(T element){ insert(element , size); } //在指定位置处添加一个元素 private void insert(T element, int index) { if(index < 0 || index > size){ throw new IndexOutOfBoundsException("数组下标越界!"); } ensureCapacity(index+1); System.arraycopy(elementData, index, elementData, index+1, size-index); elementData[index] = element; size++; } private void ensureCapacity(int size) { if(size > capacity){ //容量增大两倍,即为原来的3倍 capacity = capacity + capacity<<1; //如果其值比最大值还大 capacity = capacity >Integer.MAX_VALUE ? hugeCapacity(size):capacity; elementData = Arrays.copyOf(elementData, capacity); } } //如果值比MAX_ARRAY_SIZE还大,那么其返回值就是Integer.MAX_VALUE,否则就是MAX_ARRAY_SIZE private static int hugeCapacity(int minCapacity) { return minCapacity > MAX_ARRAY_SIZE ? Integer.MAX_VALUE : MAX_ARRAY_SIZE; } //删除顺序线性表中指定索引处的元素 public T remove(int index){ if(index < 0 || index > size-1){ throw new IndexOutOfBoundsException("所要删除元素的索引越界"); } T oldData = (T)elementData[index]; System.arraycopy(elementData, index+1, elementData, index, size-(index+1)); elementData[size-1] = null; size--; return oldData; } //获取顺序线性表中索引为i处的元素 public T get(int i) { if (i < 0 || i > size - 1){ throw new IndexOutOfBoundsException("数组下标越界!"); } return (T)elementData[i]; } public String toString() { if (size == 0) { return "[]"; } else { StringBuilder sb = new StringBuilder("["); for (int i = 0 ; i < size ; i++ ) { sb.append(elementData[i].toString() + ", "); } int len = sb.length(); return sb.delete(len - 2 , len).append("]").toString(); } } public static void main(String[] args) { SinglyLinkedList<String> list = new SinglyLinkedList<String>(); System.out.println(list); list.add("a"); System.out.println(list); list.add("b"); System.out.println(list); list.add("c"); System.out.println(list); list.add("d"); System.out.println(list); list.add("e"); System.out.println(list); list.remove(2); System.out.println("remove之后:" + list); System.out.println(list.get(2)); } }
2.线性表的链式实现,是一个双向链表,类似LinkedList
package collectionsFramework.linearlist; /** * @Package collectionsFramework.linkedlist * * @ClassName: DoublyLinkedList * * @Description: TODO(LinkedList的增删改查) * * @author andy * * @date 2013-11-21 下午05:40:31 */ public class DoublyLinkedList<T> { private class Node<T> { private T data; private Node<T> prev; private Node<T> next; public Node() { } public Node(T data, Node<T> prev, Node<T> next) { this.data = data; this.prev = prev; this.next = next; } } private Node<T> header; private Node<T> tail; private int size; public DoublyLinkedList() { header = null; tail = null; } // 返回链表的长度 public int length() { return size; } public boolean empty() { return size == 0; } //在链表尾部添加新节点 public T add(T element) { if (empty()) { header = new Node<T>(element, null, null); tail = header; } else{ Node<T> newNode = new Node<T>(element , tail, null); tail.next = newNode; tail = newNode; } size++; return element; } //在链表头部添加新节点 public T addFirst(T element) { header = new Node<T>(element, null, header); if(empty()){ tail = header; } size++; return element; } public T addLast(T element) { return add(element); } //指定位置出插入元素 public T add(int index, T element) { if (index < 0 || index > size) { throw new IndexOutOfBoundsException("线性表索引越界"); } // 如果还是空链表 if (empty()) { add(element); } else { if(index == 0){ addFirst(element); }else{ //插入点的前一个结点 Node<T> prev = getNudeByIndex(index-1); //a、b、c、d //在c这是插入一个e结点,并且它的prev指向上面的b,它的next指向d,但是b的next引用和d的prev引用还是没有变 Node<T> newNode = new Node<T>(element, prev, prev.next); //b的next引用指向e prev.next = newNode; //d的prev引用指向e prev.next.prev = newNode; size++; } } return element; } //根据索引index获取指定位置的节点,二分法查找元素 public Node<T> getNudeByIndex(int index){ if (index < 0 || index > size) { throw new IndexOutOfBoundsException("线性表索引越界"); } if(empty()){ return null; } if(index <= size/2){ int i=0; for(Node<T> currentNode = header; i <= size/2 && currentNode!=null; i++,currentNode=currentNode.next){ if(i == index){ return currentNode; } } }else{ int i=size-1; for(Node<T> currentNode = tail; i > size/2 && currentNode!=null; i--,currentNode=currentNode.prev){ if(i == index){ return currentNode; } } } return null; } //获取但不移除此列表的头(第一个元素)。 public T element() { return getFirst(); } //获得指定索引出的数据 public T get(int index) { if (index < 0 || index > size - 1) { throw new IndexOutOfBoundsException("线性表索引越界"); } return getNudeByIndex(index).data; } public T getFirst() { return header == null? null:header.data; } public T getLast() { return tail == null? null:tail.data; } public T offer(T element) { return add(element); } public T offerFirst(T element) { return addFirst(element); } public T offerLast(T element) { return addLast(element); } public T peek() { return getFirst(); } public T peekFirst() { return getFirst(); } public T peekLast() { return getLast(); } public T poll() { return removeFirst(); } public T pollFirst() { return removeFirst(); } public T pollLast() { return removeLast(); } public T pop() { return removeFirst(); } public T push(T element) { return addFirst(element); } public T remove() { return remove(0); } public T remove(int index) { if(index < 0 || index > size -1){ throw new IndexOutOfBoundsException("线性表索引越界"); } if(empty()){ return null; } Node<T> delNode; if(index == 0){ //a、b、c、d、e 移除a结点,下面得到a结点 delNode = header; //将b结点设置为头结点 header = delNode.next; //并将b结点对上一个a节点的引用设置为空 delNode.next.prev = null; //并将a结点对下一个b结点的引用设置为空 delNode.next = null; //将删除结点设置为空 //delNode.data = null; //delNode = null; size--; return delNode.data; }else if(index == (size-1)){ //a、b、c、d、e 移除e结点,下面得到e结点 delNode = tail; //得到d结点,并将d结点的下一点指向null delNode.prev.next = null; //并将e结点对上一个节点的引用设置为null delNode.prev = null; //将删除结点设置为空 //delNode.data = null; //delNode = null; size--; return delNode.data; }else{ //a、b、c、d、e 移除c结点,下面得到c结点 delNode = getNudeByIndex(index); //得到b结点,并将b结点的下一点指向d结点 delNode.prev.next = delNode.next; //并将d结点对上一个节点的引用设置为b delNode.next.prev = delNode.prev; //并将c结点对b、d的引用设置为空 delNode.next = null; delNode.prev = null; size--; return delNode.data; } } public T removeFirst() { return remove(0); } public T removeLast() { return remove(size-1); } public void clear() { if(empty()){ return; } for (Node<T> node = header; node != null; node = node.next) { node.data = null; node.prev = null; node.next = null; } header = null; tail = null; size = 0; } public String toString() { //链表为空链表时 if (empty()) { return "[]"; } else { StringBuilder sb = new StringBuilder("["); for (Node<T> current = header ; current != null ; current = current.next ) { sb.append(current.data.toString() + ", "); } int len = sb.length(); return sb.delete(len - 2 , len).append("]").toString(); } } public static void main(String[] args) { DoublyLinkedList<String> linkedList = new DoublyLinkedList<String>(); System.out.println(linkedList); linkedList.add("a"); linkedList.add("b"); linkedList.add("c"); linkedList.add("d"); System.out.println(linkedList); System.out.println("移除对象:" + linkedList.removeFirst()); System.out.println(linkedList); System.out.println("移除对象:" + linkedList.remove(2)); System.out.println(linkedList); } }
一步一个脚印,方便自己复习,欢迎大家指正,非常感谢,共同进步!
posted on 2013-11-25 23:40 lovebeauty 阅读(486) 评论(0) 编辑 收藏 举报