双向链表的Python代码实现

一、双向链表

  • 双向链表

    • 既可以从头遍历到尾, 又可以从尾遍历到头

    • 也就是链表相连的过程是双向的. 那么它的实现原理, 你能猜到吗?

    • 一个节点既有向前连接的引用, 也有一个向后连接的引用.

    • 双向链表可以有效的解决单向链表中提到的问题.

    • 双向链表有什么缺点呢?

      • 每次在插入或删除某个节点时, 需要处理四个节点的引用, 而不是两个. 也就是实现起来要困难一些

      • 并且相当于单向链表, 必然占用内存空间更大一些.

      • 但是这些缺点和我们使用起来的方便程度相比, 是微不足道的.

  • 双向连接的图解:

1.双向链表的创建

  • 创建一个双向链表的类

    #创建节点类
    class Node:
        def __init__(self,element):
            self.element = element
            self.next = None
            self.prev = None
    ​
    #创建双向链表类
    class doubly_linked_list:
        #定义属性
        def __init__(self, element):
            self.length = 0
            self.head = None
            self.tail = None
        #定义操作方法:
        #def x1(self):
        #def x2(self):
  • 代码解析:

    • Node中添加一个self.prev属性,该属性指向上一个结点

    • 另外添加一个self.tsil属性,用于指向末尾的结点

2.尾部追加数据

 def append(self,element):
        # 1.根据元素创建节点
        newNode = Node(element)
​
        # 2.判断列表是否为空列表
        if self.head == None:
            self.head = newNode
            self.tail = newNode
        else:
            self.tail.next = newNode
            newNode.prev = self.tail
            self.tail = newNode
​
        length + 1
        self.length+=1
  • 代码解析:

    • 代码1部分通过元素创建新的节点.

    • 代码2部分分两种情况.

    • 情况一: 链表原来为空

      • 链表中原来如果没有数据, 那么直接让head和tail指向这个新的节点即可.

    • 情况二: 链表中已经存在数据

      • 将数据默认追加到尾部.

3.任意位置插入

   
    def insert(self,position, element):
        #判断越界的问题
        if position < 0 or position > self.length:
            return False
    
        newNode = Node(element)
     
        if position == 0:
            #判断链表是否为空
            if self.head == None:
                self.head = newNode
                self.tail = newNode
            else:
                self.head.prev = newNode
                newNode.next = self.head
                self.head = newNode
​
        elif position == self.length: 
            self.tail.next = newNode
            newNode.prev = self.tail
            self.tail = newNode
        else: # 在中间位置插入数据
            index = 0
            current = self.head
            previous = None
            #查找正确的位置
            while index < position:
                previous = current
                current = current.next
                index+=1
            #交换节点的指向顺序
            newNode.next = current
            newNode.prev = previous
            current.prev = newNode
            previous.next = newNode
       
        self.length+=1
        return True
  • 代码深度解析, 代码比较复杂, 我们分成三种情况:

    • 情况一: 将元素插入到头部(position === 0)

  • 情况二: 将元素插入到尾部(position === length)
  • 情况三: 将元素插入到中间位置

4.位置移除数据

​
    def removeAt(self, position):
        # 判断越界的问题
        if position < 0 or position >= self.length:
            return None
​
        # 判断移除的位置
        current = self.head
        if position == 0:
            if self.length == 1:
                self.head = None
                self.tail = None
            else:
                self.head = self.head.next
                self.head.prev = None
        elif position == self.length - 1:
            current = self.tail
            self.tail = self.tail.prev
            self.tail.next = None
        else:
            index = 0
            previous = None
            while index < position:
                previous = current
                current = current.next
                index += 1
            previous.next = current.next
            current.next.prev = previous
​
        length-1
        self.length -= 1
        return current.element
  • 情况一: 删除头部的元素

  • 情况二: 删除尾部的元素

  • 情况三: 删除中间位置的元素

5.获取元素位置

    # 根据元素获取再链表中第一个出现的位置, 没有返回 - 1
    def indexOf(self,element):
        #1.定义变量保存信息
        current = self.head
        index = 0
        #2.查找正确的信息
        while current:
            if current.element == element:
                return index
            index+=1
            current = current.next
        #3.来到这个位置, 说明没有找到, 则返回-1
        return -1

6.根据元素删除

    #根据元素删除
    def remove(self,element):
        index = self.indexOf(element)
        return self.removeAt(index)

7.其他方法实现

    # 判断是否为空
    def isEmpty(self):
        return self.length == 0
​
    # 获取链表长度
    def size(self):
        return self.length
​
    # 获取第一个元素
    def getHead(self):
        return self.head.element
​
    # 获取最后一个元素
    def getTail(self):
        return self.tail.element

 

 

  • 22
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
双向链表(Doubly Linked List)是一种数据结构,其中每个节点都有两个指针,分别指向前一个节点和后一个节点。在Python中,我们可以使用类来实现双向链表。下面是一个简单的双向链表实现示例: ```python class Node: def __init__(self, data): self.data = data self.prev = None self.next = None class DoublyLinkedList: def __init__(self): self.head = None # 插入节点到链表头部 def insert_at_start(self, data): new_node = Node(data) if self.head is not None: new_node.next = self.head self.head.prev = new_node self.head = new_node # 在链表尾部插入节点 def insert_at_end(self, data): new_node = Node(data) if self.head is not None: cur_node = self.head while cur_node.next: cur_node = cur_node.next cur_node.next = new_node new_node.prev = cur_node else: self.head = new_node # 删除指定节点 def delete_node(self, key): cur_node = self.head if cur_node and cur_node.data == key: self.head = cur_node.next if self.head: self.head.prev = None return prev_node = None while cur_node and cur_node.data != key: prev_node = cur_node cur_node = cur_node.next if cur_node is None: return prev_node.next = cur_node.next if cur_node.next: cur_node.next.prev = prev_node # 遍历并打印链表 def print_list(self): cur_node = self.head while cur_node: print(cur_node.data, end=" <-> ") cur_node = cur_node.next print("None") # 使用示例 dll = DoublyLinkedList() dll.insert_at_start(3) dll.insert_at_start(1) dll.insert_at_end(4) dll.print_list() # 输出: 1 <-> 3 <-> 4 <-> None dll.delete_node(3) dll.print_list() # 输出: 1 <-> 4 <-> None ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值