单向链表
单向链表也叫单链表,是链表中最简单的一种形式,它的每个节点包含两个域,一个信息域(元素域)和一个链接域。这个链接指向链表中的下一个节点,而最后一个节点的链接域则指向一个空值。
- 表元素域elem用来存放具体的数据。
- 链接域next用来存放下一个节点的位置(python中的标识)
- 变量p指向链表的头节点(首节点)的位置,从p出发能找到表中的任意节点。
节点的实现
class SingleNode(object): """单链表的节点""" def __init__(self, item): # item存放数据元素 self.item = item # next是下一个节点的标识 self.next = None
测试
# 创建两个节点 s1 = SingleNode(10) s2 = SingleNode(12) # 将节点2绑定到节点1的next属性上 s1.next = s2 print('s1:', s1.item) # s1: 10 print('s2:', s1.next.item) # s2: 12
单链表的操作
- is_empty() 链表是否为空
- length() 链表长度
- travel() 遍历整个链表
- add(item) 链表头部添加元素
- append(item) 链表尾部添加元素
- insert(pos, item) 指定位置添加元素
- remove(item) 删除节点
- search(item) 查找节点是否存在
单链表的实现
class SingleLinkList(object): """单链表""" def __init__(self): self.head = None def is_empty(self): """判断链表是否为空""" return self.head is None def length(self): """计算链表长度""" # cur初始时指向头节点 cur = self.head count = 0 # cur指向None,说明到达了尾节点 while cur is not None: count += 1 cur = cur.next return count
遍历链表
def travel(self): """遍历链表""" cur = self.head while cur is not None: print(cur.item) cur = cur.next
头部添加元素
def add(self, item): """头部添加元素""" # 创建一个保存item值的节点 node = SingleNode(item) # 将新节点的链接域指向头节点 node.next = self.head # 将链表的头head指向新节点 self.head = node
尾部追加元素
def append(self, item): """尾部追加元素""" # 创建一个保存item值的节点 node = SingleNode(item) # 先判断链表是否为空,若是空链表,则将head指向新节点 if self.is_empty(): self.head = node # 若不为空,则找到尾部,将尾节点的next指向新节点 else: cur = self.head # 遍历链表,找到最后一个节点 while cur.next is not None: cur = cur.next cur.next = node
在指定位置添加元素
def insert(self, pos, item): """在指定位置添加元素""" # 如果指定位置pos在第一个元素之前,则执行头部插入 if pos <= 0: self.add(item) # 如果指定元素超过链表尾部,则执行尾部插入 elif pos > (self.length()-1): self.append(item) # 中间位置插入 else: node = SingleNode(item) # pre_node用来指向指定位置pos的前一个节点pos-1,从头节点开始移动到指定位置 pre_node = self.head num = 0 while num < pos - 1: num += 1 pre_node = pre_node.next # 把新节点的链接域指向插入的下一个节点 node.next = pre_node.next # 把插入的前一个节点的链接域指向新节点 pre_node.next = node
删除元素
def remove(self, item): """删除节点""" cur = self.head pre = None while cur is not None: # 找到了指定元素 if cur.item == item: # 如果第一个就是删除的节点 if not pre: # 将头指针指向头节点的后一个节点 self.head = cur.next else: # 将删除位置的前一个节点的next指向删除位置的后一个节点 pre.next = cur.next return else: # 继续按链表后移节点 pre = cur cur = cur.next else: raise ValueError('Can not find the item!')
查找节点是否存在
def search(self, item): """链表查找节点是否存在,并返回true或者false""" cur = self.head while cur is not None: if cur.item == item: return True cur = cur.next return False
测试
if __name__ == '__main__': lst1 = SingleLinkList() lst1.append(1) lst1.append('a') lst1.add(0) lst1.insert(2, 'h') print('length:', lst1.length()) # length: 4 lst1.travel() # 0 1 h a lst1.remove(1) lst1.remove('h') print('length:', lst1.length()) # 2 lst1.travel() # 0 a print(lst1.is_empty()) # False