- 链表
- 采用链表来实现无序表
- 实现节点ListNode
- 链表实现无序表UnorderList
- 有序表及其实现
- 总结
链表(linked list)是一种常见的基础数据结构,是一种线性表,但是并不会按线性的顺序存储数据,而是在每一个节点里存到下一个节点的指针(Pointer)。
由于不必须按顺序存储,链表在插入的时候可以达到O(1)的复杂度,比另一种线性表顺序表快得多,但是查找一个节点或者访问特定编号的节点则需要O(n)的时间,而顺序表相应的时间复杂度分别是O(logn)和O(1)。
数组是很常用的数据储存方式,而链表就是继数组之后,第二种最通用的数据储存方式了。数组需要存放在连续的空间,计算机很容易实现。而链表的好处是不用确定空间长度,不够的时候,直接申请新的节点,帮助插入。所以链表可以更灵活地进行内存分配。
链表(linked list)是一种序列形的数据结构,其中包含了很多通过链接 (link) 被串起来的节点。每个节点有一个数据域,储存着节点的数值,还有一个指针域,指向下一个节点。
-
单链表:链表中最简单的一种是单向链表,它包含两个域,一个信息域和一个指针域。这个链接指向列表中的下一个节点,而最后一个节点则指向一个空值。
-
双链表:双链表是为了解决链表节点不知道前面节点的尴尬,于是在节点的定义中,存在一个父节点,和一个子节点。这样就能顺着父节点往回找。
-
循环链表:在一个 循环链表中, 首节点和末节点被连接在一起。这种方式在单向和双向链表中皆可实现。
主要应用:链表用来构建许多其它数据结构,如堆栈,队列和他们的派生。
- 数据存放位置美哦与规则,数据项之间建立链接指向,保持相对位置;
- 每个节点至少包含两个信息:数据项本身,及指向下一个节点的引用信息。
class ListNode(object): # 初始化 def __init__(self, val, next=None): self.val = val self.next = next # 返回数据项 def get_Val(self): return self.val # 返回下一个节点 def get_Next(self): return self.next # 修改数据项 def set_Val(self,newval): self.val = newval # 修改下一个节点 def set_Next(self,newnext): self.next = newnext链表实现无序表UnorderList
- 链接节点构建数据集;
- 如果想要访问列表中的所有节点,就必须从第一个遍历下去;
无序表必须引用第一个节点:
class UnorderList(object): def __init__(self): self.head = None
判断表是否为空
def isEmpty(self): return self.head == None
add方法
我们给链表添加数据,新数据项可以加入到原表的任何位置,考虑性能,我们添加到最容易添加的地方,表头。
size()方法
从链条头head开始遍历到表尾用变量累加经过的节点数。
search方法
从表头head开始遍历到表尾,同时判断当前节点的数据项是否是目标。
remove方法
首先找到目标,然后current指向当前匹配的数据项的节点;然后把前一个节点的next指向下一个节点;所有这里需要当前节点还有前一个节点的引用。
class UnorderList(object): def __init__(self): self.head = ListNode() def isEmpty(self): return self.head.val == None def add(self, item): newnode = ListNode(item, None) newnode.set_Next(self.head) self.head = newnode def size(self): current = self.head count = 0 while current != None: count = count + 1 current = current.get_Next() return count-1 def search(self, item): current = self.head found = False while current != None and not found: if current.get_Val() == item: found = True else: current = current.get_Next() return found def remove(self, item): current = self.head previous = None found = False while not found: if current.get_Val() == item: found = True else: previous = current current = current.get_Next() if previous == None: self.head = current.get_Next() else: previous.set_Next(current.get_Next())
l = UnorderList() print(l.isEmpty()) l.add(4) l.add(5) l.add(6) print(l.size()) l.remove(6) print(l.search(5)) print(l.size())
输出: True 3 True 2有序表及其实现
有序表是一种数据项按照其可比性质(如整数大小、字母先后)来决定在列表中的位置;越小的数据项越靠近表头,越靠前。
对比无序表,可以发现节点定义相同,对于isEmpty、size、remove这些方法与节点次序是无关的,所以两者相同;
而search/add方法需要修改。
- 在无序表中,查找需要遍历所有链表;而有序表则不需要,因为当前节点数据项大于所查找的数据后就不需要向后查找了(链表有序排列特性);
- add方法在添加数据时,需要添加到合适位置,不能仅仅是添加在表头了,保证链表的有序性。
def add(self, item): current = self.head previous = None stop = False while current.get_Val() != None and not stop: if current.get_Val() > item: stop = True else: previous = current current = current.get_Next() temp = ListNode(item, None) if previous == None: temp.set_Next(self.head) self.head = temp else: temp.set_Next(current) previous.set_Next(temp)
def search(self, item): current = self.head found = False stop = False while current != None and not found and not stop: if current.get_Val() == item: found = True else: if current.get_Val() > item: stop = True else: current = current.get_Next() return found总结
- 对于链表的复杂度,主要看对应的方法是否涉及到链表的遍历;
isEmpty是O(1);size是O(n);
search/remove/add(有序)O(n);
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)