美文网首页
八、核心数据结构

八、核心数据结构

作者: 胖虎喜欢小红 | 来源:发表于2020-01-07 20:52 被阅读0次

    一、什么是数据结构

    在计算机科学中,数据结构(英语:data structure)是计算机中存储、组织数据的方式。

    1. Python 中核心数据结构分类

    • 序列类型: 字符串、列表、元组
    • 泛映射类型: 字典
    • 集合: set()

    在 Python中列表、元组、字典、集合都称为容器。

    1. 序列类型数据结构共有的特点:
    • 序列类型中的元素都有对应的位置,这个位置叫偏移量或者索引
        偏移量(索引)     0   1   2   3   N-1
        
                           1   2   3   4    5
                           
        偏移量(索引)     -n  -4  -3  -2   -1
    

    二、列表

    1、列表的特性

    列表内的元素是可变的。
    列表的元素可以是 Python 的任何类型的数据和对象

    如:字符串、列表、元组、字典、集合、函数、类

    列表中的具有相同值的元素允许出现多次

    [1, 2, 1, 1, 1, 1, 3, 3, 2]
    

    2、创建列表

    In [124]: li=[]  
    
    In [125]: li                                                                         
    Out[125]: []
    
    In [126]: li=['a',1]                                                                 
    
    In [127]: li                                                                         
    Out[127]: ['a', 1]
    
    In [128]: list('hello')            //list() 从其他类型转换  
    Out[128]: ['h', 'e', 'l', 'l', 'o']
    
    In [129]: 'www.baidu.com'.split('.')     //split()从字符串转换   
    Out[129]: ['www', 'baidu', 'com']
    

    嵌套的列表

    列表中可包含 python 中任何类型的元素(对象),当然也可以包括一个或多个列表

    li = [['one', 'two', 'three'], [1, 2, 3],a,b]
    

    列表的基本操作

    1、取值

    没有嵌套的列表

    In [130]: a = [ 'insert', 'append','extend', 'remove', 'pop', 'sort', 'sorted']      
    
    In [131]: a[0]                                                                       
    Out[131]: 'insert'
    

    嵌套的列表

    In [132]: a = [['one', 'two', 'three'], [1, 2, 3]]                                   
    
    In [133]: a[1][1]                                                                    
    Out[133]: 2
    

    2、切片

    同字符串的切片一样

    In [134]: li = [ 'insert', 'append','extend', 'remove', 'pop', 'sort', 'sorted']     
    
    In [135]: li[:]       //获取全部的值
    Out[135]: ['insert', 'append', 'extend', 'remove', 'pop', 'sort', 'sorted']
    
    In [136]: li[::-1]         //反转
    Out[136]: ['sorted', 'sort', 'pop', 'remove', 'extend', 'append', 'insert']
    
    In [137]: li[0:3]                                                                    
    Out[137]: ['insert', 'append', 'extend']
    

    3、必须掌握

    #先定义一个列表
    li=[1,3,2,8,6,0]
    

    len()

    len是一个内置函数,可以统计序列类型的数据结构的长度
    
        In [139]: len(li)                                                                    
        Out[139]: 6
    

    in

    判断元素是否存在于列表中
    
        if 5 in li:
            print('我存在')
        else:
            print('不存在')
    

    append() (修改了列表)本身

    向列表的最后位置,添加一个元素,只接收一个参数。
    
        n [141]: li.append(3)                                                               
        
        In [142]: li                                                                         
        Out[142]: [1, 3, 2, 8, 6, 0, 3]
    

    insert()

    向原列表的指定位置插入一个元素,接收两个参数,
    
    第一个是索引号,第二个是要插入的元素。
    
        In [143]: li                                                                         
        Out[143]: [1, 3, 2, 8, 6, 0, 3]
        
        In [144]: li.insert(1,9)                                                             
        
        In [145]: li                                                                         
        Out[145]: [1, 9, 3, 2, 8, 6, 0, 3]
    

    extend()

    可以把一个序列类型中的每个元素追加到原列表中,接收的参数是一个序列类型的数据(字符串,列表)
    
        In [146]: l2=[9,8]                                                                   
        
        In [147]: li.extend(l2)                                                              
        
        In [148]: li                                                                         
        Out[148]: [1, 9, 3, 2, 8, 6, 0, 3, 9, 8]
    

    remove()

    移除列表中某个指定的元素,没有返回值,并且假如有多个相同值的元素存在,每次只会移除排在最前面的那个
    
        In [148]: li                                                                         
        Out[148]: [1, 9, 3, 2, 8, 6, 0, 3, 9, 8]
        
        In [149]: li.remove(3)                                                               
        
        In [150]: li                                                                         
        Out[150]: [1, 9, 2, 8, 6, 0, 3, 9, 8]
    

    pop()

    从原列表中删除一个元素,并且把这个元素返回。接收零个或一个参数,参数是偏移量,int 类型。
    
        删除列表中的最后一个元素
        li.pop() 
        
        删除列表中第二个索引号对应的元素,并且返回这个元素,用变量名`n` 接收。  
        n = li.pop(2)
    

    ''.join() 把列表中的元素拼接起来,返回的是字符串类型

    l7 = ['a','b']
    s = ''.join(l7)
    print(s)
    
    输出
    'ab'
    

    还可以以指定的字符进行拼接

    l7 = ['a','b']
    s = '-'.join(l7)
    print(s)
    
    # 输出
    'a-b'
    

    index 返回指定元素的索引号。

    In [150]: li                                                                         
    Out[150]: [1, 9, 2, 8, 6, 0, 3, 9, 8]
    
    In [153]: li.index(3)     //3是指定的元素                                                           
    Out[153]: 6
    

    count() 是列表的内置方法,可以统计出相同值的元素在列表中总共出现都少次.

    In [150]: li                                                                        
    Out[150]: [1, 9, 2, 8, 6, 0, 3, 9, 8]
    
    In [155]: li.count(8)                                                               
    Out[155]: 2
    

    sort()

    是列表的内置方法,对列表中元素进行排序。

    默认是升序, 这个改变列表自身。

    还可以接收一个 reverse (反转) 参数, 其值可以是 True 和 False。

    False 是升序,True 是降序。需要是同一种数据类型,比如都是字符串,或都是整型。

    In [157]: li                                                                       
    Out[157]: [1, 9, 2, 8, 6, 0, 3, 9, 8]
    
    In [158]: li.sort()                                                                
    
    In [159]: li                                                                       
    Out[159]: [0, 1, 2, 3, 6, 8, 8, 9, 9]
    ===================================================
    In [160]: li.sort(reverse=True)                                                    
    
    In [161]: li                                                                       
    Out[161]: [9, 9, 8, 8, 6, 3, 2, 1, 0]
    

    4、通过索引号和切片修改列表

    索引号

    In [11]: number = [1,2,3,4,5]
        
    In [12]: number[2]=20       //把索引号为2的元素替换成20
        
    In [13]: number
    Out[13]: [1, 2, 20, 4, 5]
    

    切片

    In [164]: li = [1, 2, 3, 4, 5]                                                     
    
    In [165]: li[1:3]=[0]        //把索引号为1,2的切片,然后替换成0
    
    In [166]: li                                                                       
    Out[166]: [1, 0, 4, 5]
    

    5、引用赋值

    n [167]: li = [1, 2, 3, 4, 5]                                                     
    
    In [168]: a=li                                                                     
    
    In [169]: a                                                                        
    Out[169]: [1, 2, 3, 4, 5]
    
    In [170]: a[-2]=[2]                                                                
    
    In [171]: a                                                                        
    Out[171]: [1, 2, 3, [2], 5]
    
    In [172]: li                                                                       
    Out[172]: [1, 2, 3, [2], 5]
    

    可以看到,这种用等号将一个列表赋值给多个变量时,使用其中任意一个变量对列表的操作,结果都会同步到其他变量的值。

    在这种现象中,就像前面学到的变量的赋值,变量和列表本身之间的关系称作,变量对列表对象的引用,并没有创建一个新的列表

    解决方法

    • 使用以下任意一种方法,都可以将原列表的值赋值给一个新的列表
    1. 列表的内置函数 obj.copy()
    2. 序列类型函数 list(obj)
    3. 列表切片

    以上方法得到的列表可赋值给一个新的变量, 这变量各自有自己的列表对象,互相之间不会影响

    点我可视化你的代码
    深浅拷贝

    浅拷贝

    In [185]: a=[1,2,3]
    
    In [187]: new_a=list(a)                                                            
    
    In [188]: new_a                                                                    
    Out[188]: [1, 2, 3]
    
    In [189]: b=a.copy()                                                               
    
    In [190]: b                                                                        
    Out[190]: [1, 2, 3]
    
    In [192]: new_a[2]=5     //把new_a索引号为2的元素替换成5
    
    In [193]: new_a                                                                    
    Out[193]: [1, 2, 5]
    
    In [194]: b                                                                        
    Out[194]: [1, 2, 3]      //b并没有发生改变
    
    In [195]: a              //a也没有改变                                                        
    Out[195]: [1, 2, 3]
    
    In [199]: a = ['name',['money',100.00]]                                            
    
    In [200]: id(a)                                                                    
    Out[200]: 139879242909704
    
    In [201]: b=list(a)                                                                
    
    In [202]: id(b)                                                                    
    Out[202]: 139879242427400
    
    In [204]: b[1][1]=20            //改变嵌套列表中的元素                                                
    
    In [205]: id(a[-1])             //但是a和b的嵌套的列表id号还是一样的                                                           
    Out[205]: 139879242878280
    
    In [206]: id(b[-1])                                                                
    Out[206]: 139879242878280
    
    In [207]: b                                                                        
    Out[207]: ['name', ['money', 20]]       //所以b改变了嵌套列表中的元素a还是会改变
    
    In [208]: a                                                                        
    Out[208]: ['name', ['money', 20]]
    
    In [209]: b[0]=age                                                                 
    
    In [210]: a                                                                        
    Out[210]: ['name', ['money', 20]]        //如果只更改外层元素,就不会一起别改变
    
    In [211]: b                                                                        
    Out[211]: ['age', ['money', 20]]
    

    深拷贝

    导入模块
    import copy 
    
    base_count = ['name',['money',100.00]]
    
    利用模块中的 copy 方法创建一个全新的对象
    xmen_new = copy.deepcopy(base_count)
    
    利用模块中的 copy 方法创建另一个全新的对象
    xpan_new = copy.deepcopy(base_count)
    
    改变其中一个对象中的值
    xpan_new[1][1] = 50.00
    
    分别打印两个对象
    print(xmen_new)
    
    print(xpan_new)
    

    三、元组

    1 元组特性介绍

    • 元组和列表一样,也是一种序列。
    • 唯一的不同是,元组是相对不可变的。

    2 高效创建元组

    t1 = ()    # 创建 空 元素的元组
    

    单一元素元组

    创建非空元素的元组是用逗号,而不是用小括号

    In [168]: v_tp = (3)
    
    In [169]: only_tp = 3,
    
    In [170]: type(v_tp)
    
    Out[170]: int
    
    In [171]: type(only_tp)
    Out[171]: tuple
    

    tuple()

    可以对其他序列类型的数据转换为元组

    In [173]: s1 = 'car'
    
    In [174]: li = [1,2,3]
    
    In [175]: tuple(s1)
    Out[175]: ('c', 'a', 'r')
    
    In [176]: tuple(li)
    Out[176]: (1, 2, 3)
    
    In [177]: dl = [1,2,3,['a','b']]
    
    In [178]: tuple(dl)
    Out[178]: (1, 2, 3, ['a', 'b'])
    
    In [33]: t1 = (1, 2, 3, ['a', 'b'])
    In [34]: t1[3][0]=0         //元组相对是不能修改的,但是可以修改元组中的列表里的元素
    In [35]: t1
    Out[35]: (1, 2, 3, [0, 'b'])
    

    使用元组的理由

    1. 占用内存空间小
    2. 元组内的值不会被意外的修改
    3. 可作为字典的键
    4. 函数的参数是以元组形式传递的
    5. 命名元组有时候可以代替类的对象

    相关文章

      网友评论

          本文标题:八、核心数据结构

          本文链接:https://www.haomeiwen.com/subject/qnudactx.html