单链表实现
主要实现有:
1 获取首尾元素
2 是否包含某元素
3.1 尾部添加
3.2 头部添加
3.3 某节点后插入
3.4 某节点前插入
4.1 尾部删除
4.2 头部删除
4.3 某节点后删除
5 删除第k个元素
6 删除元素值为key的所有节点
7 链表反转(逆置)
8 获取k 位置上的节点
9 迭代器的实现
Java实现
package com.base;
import java.util.Iterator;
import java.util.NoSuchElementException;
/**
* 自定义单链表各功能的实现
*
* @author Administrator
*
* @param <Item>
*/
public class LinkedList<Item> implements Iterable<Item> {
private class Node {
private Item item;
private Node next;
}
private Node first;
private Node last;
private int N;
public LinkedList() {
first = null;
last = null;
}
public LinkedList(Item[] a) {
for (Item i : a)
append(i);
}
public LinkedList(Iterable<Item> coll) {
for (Item i : coll)
append(i);
}
public boolean isEmpty() {
return first == null;
}
public int size() {
return N;
}
/**
* 返回头尾节点元素
*
* @return
*/
public Item first() {
if (isEmpty())
throw new RuntimeException("链表为空");
return first.item;
}
public Item last() {
if (isEmpty())
throw new RuntimeException("链表为空");
return last.item;
}
/**
* 是否含有某元素
*
* @param item
* @return
*/
public boolean contains(Item item) {
Node curr = first;
while (curr != null && !curr.item.equals(item))
curr = curr.next;
return curr != null;
}
/**
* 末尾追加
*
* @param item
*/
public void append(Item item) {
Node oldLast = last;
Node last = new Node();
last.item = item;
last.next = null;
if (isEmpty())
first = last;
else
oldLast.next = last;
N++;
}
/**
* 头部添加
*
* @param item
*/
public void prepend(Item item) {
Node x = new Node();
x.item = item;
if (isEmpty()) {
first = x;
last = x;
} else {
x.next = first;
first = x;
}
N++;
}
/**
* 某节点后插入
*/
public void insertAfter(Node a, Node b) {
if (a != null && b != null) {
if (last == a)
last = b;
b.next = a.next;
a.next = b;
N++;
}
}
/**
* 某节点之前插入节点
*/
public void insertBefore(Node a, Node b) {
if (a != null && b != null) {
if (first == a) {
b.next = a;
first = b;
} else {
Node prev = null, curr = first;
while (curr.next != null) {
if (curr.next == a) {
prev = curr.next;
prev.next = b;
b.next = a;
break;
}
}
}
N++;
}
}
/**
* 尾部删除
*
* @return
*/
public Item removeLast() {
if (isEmpty())
throw new RuntimeException("链表为空");
if (first == last) {
Item item = first.item;
first = last = null;
N--;
return item;
}
Item item = last.item;
Node prev = null, curr = first;
while (curr.next != null) {
prev = curr;
curr = curr.next;
}
prev.next = null;
last = prev;
N--;
return item;
}
/**
* 头部删除
*/
public Item removeFirst() {
if (isEmpty())
throw new RuntimeException("链表为空");
Item item = first.item;
first = first.next;
N--;
if (isEmpty())
last = null;
return item;
}
/**
* 某节点后删除
*/
public void removeAfter(Node node) {
if (node != null && node.next != null) {
if (node.next.next == null)
last = node;
node.next = node.next.next;
N--;
}
}
/**
* 某节点前删除
*/
/**
* 删除第k个元素
*/
public Item delete(int k) {
if (k < 1)
return null;
int i = 1;
Node prev = null, curr = first;
while (i < k && curr != null) {
prev = curr;
curr = curr.next;
i++;
}
if (curr != null) {
if (prev == null)
first = curr.next;
else
prev.next = curr.next;
if (curr.next == null)
last = prev;
N--;
return curr.item;
} else
return null;
}
/**
* 链表反转
*
* 思想:将原链表的节点一个一个拆下来放到新的链表头部
*/
public void reverse() {
first = reverse(first);
setLastAndN();
}
public Node reverse(Node node) {
Node srcFirst = node;
Node destFirst = null;
while (srcFirst != null) {
Node next = srcFirst.next;
srcFirst.next = destFirst;
destFirst = srcFirst;
srcFirst = next;
}
return destFirst;
}
public void setLastAndN() {
last = first;
N = 0;
if (first != null) {
N++;
while (last.next != null) {
last = last.next;
N++;
}
}
}
/**
* 删除Item 为key的所有结点
*
* 思想:首先找到item为key的节点的位置
*/
public void remove(Item item) {
LinkedList<Integer> idx = new LinkedList<>();
int i = 1;
for (Item x : this) {
if (x.equals(item))
idx.prepend(i);
i++;
}
for (int k : idx)
delete(k);
}
/**
* 获取k位置上的节点
*/
public Node node(int k) {
if (k < 1)
return null;
int i = 1;
Node curr = first;
while (i < k && curr != null) {
curr = curr.next;
i++;
}
return curr;
}
/**
* 迭代器
*/
@Override
public Iterator<Item> iterator() {
return new ListIterator();
}
private class ListIterator implements Iterator<Item> {
private Node current = first;
@Override
public boolean hasNext() {
return current != null;
}
@Override
public Item next() {
if (!hasNext())
throw new NoSuchElementException();
Item item = current.item;
current = current.next;
return item;
}
@Override
public void remove() {
throw new UnsupportedOperationException();
}
}
}