python-链表

数据结构是计算机科学必须掌握的一门学问,很多的教材都是用C语言实现链表,因为C有指针,可以很方便的控制内存,很方便就实现链表,其他的语言,则没那么方便,有很多都是用模拟链表.

因为python是动态语言,可以直接把对象赋值给新的变量。在C/C++中,通常采用“指针+结构体”来实现链表;而在Python中,则可以采用“引用+类”来实现链表。

链表的定义:是一组数据项的集合,其中每个数据项都是一个节点的一部分,每个节点还包含指向下一个节点的链接

链表的结构:data为自定义的数据,next为下一个节点的地址。

节点

基本元素:

节点:每个节点有两个部分,左边称为值域,存放用户数据;右边部分称为指针域,用来存放指向下一个元素的指针。

head:head节点永远指向第一个节点

tail: tail永远指向最后一个节点

None:链表中最后一个节点的指针域为None值

链表种类:单向链表、单向循环链表、双向链表、双向循环链表


单向循环列表

  1、节点类定义如下,我们将节点类定义成Node,该类在初始化实例对象时,定义了两个实例变量,其中data用来存储节点的值,next用来存储下一个节点的索引:

class Node:

    def __init__(self,data = None, next = None):

        self.data = data

        self.next = next

2、定义一个节点,如下创建了三个独立的节点:

node1 = Node(1)

node2 = Node(2)

node3 = Node(3)

然后再把每个节点的关系表示出来,就OK了。

node1.next = node2

node2.next = node3

操作链表的原理知识

1.遍历链表

链表的基本操作:遍历next节点

在列表中查找一个元素

在列表中插入一个元素

从列表中删除一列元素

  不可以用head来遍历列表,否则会丢失列表的一些节点 ,可以使用和head相同类型的临时的指针变量,这个变量先初始化为链表结构的head指针,然后控制一个循环。

probe = head

while probe != None:

    probe = probe.next

插入

3.删除

#先定一个node的类

class Node():                  #value + next

    def __init__ (self, value = None, next = None):

        self._value = value

        self._next = next

    def getValue(self):

        return self._value

    def getNext(self):

        return self._next

    def setValue(self,new_value):

        self._value = new_value

    def setNext(self,new_next):

        self._next = new_next

#实现Linked List及其各类操作方法

class LinkedList():

    def __init__(self):      #初始化链表为空表

        self._head = Node()

        self._tail = None

        self._length = 0

    #检测是否为空

    def isEmpty(self):

        return self._head == None 

    #add在链表前端添加元素:O(1)

    def add(self,value):

        newnode = Node(value,None)    #create一个node(为了插进一个链表)

        newnode.setNext(self._head) 

        self._head = newnode

    #append在链表尾部添加元素:O(n)

    def append(self,value):

        newnode = Node(value)

        if self.isEmpty():

            self._head = newnode  #若为空表,将添加的元素设为第一个元素

        else:

            current = self._head

            while current.getNext() != None:

                current = current.getNext()  #遍历链表

            current.setNext(newnode)  #此时current为链表最后的元素

    #search检索元素是否在链表中   

    def search(self,value):

        current=self._head

        foundvalue = False

        while current != None and not foundvalue:

            if current.getValue() == value:

                foundvalue = True

            else:

                current=current.getNext()

        return foundvalue

    #index索引元素在链表中的位置

    def index(self,value):

        current = self._head

        count = 0

        found = None

        while current != None and not found:

            count += 1

            if current.getValue()==value:

                found = True

            else:

                current=current.getNext()

        if found:

            return count

        else:

            raise ValueError ('%s is not in linkedlist'%value)

    #remove删除链表中的某项元素

    def remove(self,value):

        current = self._head

        pre = None

        while current!=None:

            if current.getValue() == value:

                if not pre:

                    self._head = current.getNext()

                else:

                    pre.setNext(current.getNext())

                break

            else:

                pre = current

                current = current.getNext()

    #insert链表中插入元素

    def insert(self,pos,value):

        if pos <= 1:

            self.add(value)

        elif pos > self.size():

            self.append(value)

        else:

            temp = Node(value)

            count = 1

            pre = None

            current = self._head

            while count < pos:

                count += 1

                pre = current

                current = current.getNext()

            pre.setNext(temp)

            temp.setNext(current)

leetcode:

      给出两个 非空 的链表用来表示两个非负的整数。其中,它们各自的位数是按照 逆序 的方式存储的,并且它们的每个节点只能存储 一位 数字。如果,我们将这两个数相加起来,则会返回一个新的链表来表示它们的和。您可以假设除了数字 0 之外,这两个数都不会以 0 开头。

示例:

输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)

输出:7 -> 0 -> 8

原因:342 + 465 = 807

# Definition for singly-linked list.

# class ListNode:

#    def __init__(self, x):

#        self.val = x

#        self.next = None

class Solution:

    def addTwoNumbers(self, l1: ListNode, l2: ListNode) -> ListNode:

        n=l1.val+l2.val

        l3=ListNode(n % 10)

        l3.next=ListNode(n//10)

        p1=l1.next

        p2=l2.next

        p3=l3

        while True:

            if p1 and p2:

                sum=p1.val+p2.val+p3.next.val

                p3.next.val=sum%10

                p3.next.next=ListNode(sum//10)

                p1=p1.next

                p2=p2.next

                p3=p3.next

            elif p1 and not p2:

                sum=p1.val+p3.next.val

                p3.next.val=sum%10

                p3.next.next=ListNode(sum//10)

                p1=p1.next

                p3=p3.next

            elif not p1 and p2:

                sum=p2.val+p3.next.val

                p3.next.val=sum%10

                p3.next.next=ListNode(sum//10)

                p2=p2.next

                p3=p3.next

            else:

                if p3.next.val==0:

                    p3.next=None

                break

        return l3

from :https://www.cnblogs.com/kumata/p/9147077.html

单链表翻转:开始以单链表的第二个元素为循环变量,用2个变量循环向后操作,并设置1个辅助变量tmp,保存数据;时间消耗O(n),空间消耗O(1)

def reverse_linkedlist3(head):

    if head == None or head.next == None: #边界条件

        return head

    p1 = head #循环变量1

    p2 = head.next #循环变量2

    tmp = None #保存数据的临时变量

    while p2:

        tmp = p2.next  #如果没有他,p2.next这个节点以及后面的节点都将会消失

        p2.next = p1

        p1 = p2

        p2 = tmp

    head.next = None

    return p1


————————————————

版权声明:本文为CSDN博主「菜鸟知识搬运工」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。

原文链接:https://blog.csdn.net/qq_30815237/article/details/90750349

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,752评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,100评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,244评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,099评论 1 286
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,210评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,307评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,346评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,133评论 0 269
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,546评论 1 306
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,849评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,019评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,702评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,331评论 3 319
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,030评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,260评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,871评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,898评论 2 351

推荐阅读更多精彩内容

  • Python语言特性 1 Python的函数参数传递 看两个如下例子,分析运行结果: 代码一: a = 1 def...
    伊森H阅读 3,057评论 0 15
  • class Node(object): def __init__(self, value): # 元素...
    猎人1987阅读 334评论 0 0
  • Python语言特性 1 Python的函数参数传递 看两个如下例子,分析运行结果: 代码一: a = 1 def...
    时光清浅03阅读 482评论 0 0
  • 我是黑夜里大雨纷飞的人啊 1 “又到一年六月,有人笑有人哭,有人欢乐有人忧愁,有人惊喜有人失落,有的觉得收获满满有...
    陌忘宇阅读 8,532评论 28 53
  • 人工智能是什么?什么是人工智能?人工智能是未来发展的必然趋势吗?以后人工智能技术真的能达到电影里机器人的智能水平吗...
    ZLLZ阅读 3,770评论 0 5