异或链表(XOR Linked List)

一、常见的链表

1、单链表(Singly Linked List)

构成:每个节点包含数据(data)和后继节点的地址(next)

2、双向链表

构成:每个节点包含数据(data)、前驱的地址(prev)、后继的地址(next)

优势:删除或添加元素不需要移动数据,可以双向遍历

3、异或链表(XOR Linked List)

构成:每个节点包含数据(data)、前驱地址和后继地址的异或

是一种实现双向链表的方法,它 增加了代码复杂度,降低了空间复杂度,随着内存设备不断发展,空间要求降低。

小例子:有一组数,每个数都是成对出现,但是有一个数丢了,用最快的方法找出这个数。

考察到相同数字的异或为0,异或满足交换律

2、java中链表的实现

1)构建节点:

private static class Node<E> {
E item;
Node<E> next;
Node<E> prev;

Node(Node<E> prev, E element, Node<E> next) {
this.item = element;
this.next = next;
this.prev = prev;
}
}

包含数据、前驱、后继

2)定义头结点first、尾节点last


3)常用方法
添加元素add(向尾部)
void linkLast(E e) {
final Node<E> l = last;
final Node<E> newNode = new Node<>(l, e, null);
last = newNode;
if (l == null)
first = newNode;
else
l.next = newNode;
size++;
modCount++;
}

记录尾部节点-》定义一个新的节点-》将尾节点赋值为新的节点-》如果链表是空的头节点也赋值为新的节点-》否则尾节点的next指向新的元素

删除元素remove
public boolean remove(Object o) {
if (o == null) {
for (Node<E> x = first; x != null; x = x.next) {
if (x.item == null) {
unlink(x);
return true;
}
}
} else {
for (Node<E> x = first; x != null; x = x.next) {
if (o.equals(x.item)) {
unlink(x);
return true;
}
}
}
return false;
}
从头节点开始遍历,当节点值为o的时候,把这个节点从链表中去除

以下为删除节点
E unlink(Node<E> x) {
// assert x != null;
final E element = x.item;
final Node<E> next = x.next;
final Node<E> prev = x.prev;

if (prev == null) {
first = next;
} else {
prev.next = next;
x.prev = null;
}

if (next == null) {
last = prev;
} else {
next.prev = prev;
x.next = null;
}

x.item = null;
size--;
modCount++;
return element;
}




 

posted on 2018-07-26 22:53  _故乡的原风景  阅读(1276)  评论(0编辑  收藏  举报