高级特性

1.切片:
可以对数组、元组、字符串进行切片操作得到想要那一部分元素
例:
    # 创建一个0—99的数组
    >>> L = list(range(100))
    >>> L
    [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 
     11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 
     21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 
     31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 
     41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 
     51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 
     61, 62, 63, 64, 65, 66, 67, 68, 69, 70,
     71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 
     81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
     91, 92, 93, 94, 95, 96, 97, 98, 99]
    >>> L[:10]
    [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
    >>> L[-10:]
    [90, 91, 92, 93, 94, 95, 96, 97, 98, 99]
    >>> L[:10:2]
    [0, 2, 4, 6, 8]
    >>> (1,2,3,4,5)[:3]
    (1, 2, 3)
    >>> 'ASDFGH'[::2]
    'ADG'
2.迭代
    1.定义
        我们可以使用for...in...来遍历list or tuple or dict or 
        字符串中的元素,这种方法称为迭代,任何可迭代对象都可以进行迭代操作
    2.如何判断是否可迭代
        可以使用collections模块中的Iterble
        """
        警告: 
        from collections import Iterable
        Warning (from warnings module):
        File "__main__", line 1
        DeprecationWarning: Using or importing the ABCs 
        from 'collections' instead of from 'collections.abc' is deprecated,
        and in 3.8 it will stop working
        """
        例如:
            from collections import Iterable
            isinstance([1,2,3,4],Iterable)
            >>>True
            isinstance('abc',Iterable)
            >>>True
            isinstance(1234,Iterable)
            >>>False
        L = [1,2,3,4,5,6]
        for i in L:
            print(i)
        >>>1,2,3,4,5,6
        对于一个字典迭代时默认迭代它的键:
            例如:
                dict = {"name":'wang',"age":18}
                for key in dict:
                   print(key)
                >>>name
                   age
        如果想迭代它的值 dict.values
        例如:
            dict = {'name':'wang','age':18}
            for val in dict.values():
                print(val)
            >>>'wang'
                18
        如果想迭代键值对 dict.itms()
        例如:
            dict = {'name':'wang','age':18}
            for key,val in dict.items():
                print(key,val)
            >>> name wang
                age 18
        Python 内置的enumerate可以将list转变为索引—元素对
        例如:
            list = [1,2,3,4]
            for key,val in enumerate(list):
                print(key,val)
            >>> 0 1
                1 2
                2 3
                3 4
3.迭代器(Iterator)
    迭代器协议:对象必须提供一个next方法,要么返回下一项,要么终止迭代抛出StopIteration异常
    
    能够作用于for循环的对象统称为可迭代对象:Iterable,但是像list,str,file,dict等虽然可以作用于
    for循环,但是它们没有next方法,是for循环先执行它们的__iter__()方法,使它们具有了__next__()方法
            >>> l =[1,2,3]
            >>> l.__next__()
            Traceback (most recent call last):
              File "<pyshell#1>", line 1, in <module>
                l.__next__()
            AttributeError: 'list' object has no attribute '__next__'
            >>> l = l.__iter__()
            >>> l.__next__()
            1
    可以使用collections模块中的Iterble来判断一个对象是否使可迭代的
    from collections import Iterable
    print(isinstance({},Iterable))
    >>>True
    像生成器generator这样可以使用next()不断计算下一个元素的对象被称为:Iterator迭代器
    要想将list,dict,str这样的对象转变为迭代器,可以使用iter()函数
    from collections import Iterator
    print(isinstance('asdf',Iterator))    
    >>>False    
    from collections import Iterator
    print(isinstance(iter('asdf'),Iterator))    
    >>>True    
4.列表生成式:
    通过list(range(m,n))可以生成一个m到n-1的数组
    (1)要生成[x1*2,x2*2,x3*2....xn*2]的数组
        [x*2 for x in list(range(m,n))]
    (2)在上面的例子中还可以添加if语句来筛选数据:
        [x*2 for x in list(rangem,n) if x%2 == 0] # 选择列表生成器中为偶数的数做乘2运算
    (3)还可以对字典中的键值对生成列表
        例:
            >>> dict = {'a':18,'b':19,'c':20}
            >>> [k + '=' + str(v) for k,v in dict.items()]
            ['a=18', 'b=19', 'c=20']
    (4)还可以对列表中的元素使用方法,例如将列表元素中的所有大写字母替换成小写字母
        >>> L = ['Hello','World','IBM','Aplee']
        >>> [s.lower() for s in L]
        ['hello', 'world', 'ibm', 'aplee']
5.生成器(generator)
    三元表达式 :
            b = a if a == "abc" else "cba"  如果a == "abc"成立,b = “abc”,否则b = “cba”
    列表解析:
            >>> l = ['鸡蛋%s' %i for i in range(10)]
            >>> l
            ['鸡蛋0', '鸡蛋1', '鸡蛋2', '鸡蛋3', '鸡蛋4', '鸡蛋5', '鸡蛋6', '鸡蛋7', '鸡蛋8', '鸡蛋9']

    使用列表生成器可是快速生成一个列表,但是列表中的元素肯定是有限的,如果我们只是用前几个元素那么
    后面的元素就会浪费存储空间,此时我们就可以使用生成器(generator),它是将列表生成器的[]换成()
    其中的元素是你每次调用它时生成的,这样就能节省存储空间
    例如:
        >>> f = (x for x in list(range(1,11)))
        >>> next(f)
        1
        >>> next(f)
        2
        >>> for s in f:
            print(s)        
        3
        4
        ...
    上面的例子使生成器的写法之一,当要计算的元素使用列表生成器无法计算时,例如
    打印斐波拉契数列1,1,2,3,5,8,13....用列表生成器无法打印但是用一个函数
    可以轻易的打印出来
    def fib(max):
        """打印斐波拉契数列"""
        n,a,b = 0,0,1
        while n<max:
            print(b)
            a,b = b,a+b
            n+=1
        return 'done'
    >>> fib(6)
    1
    1
    2
    3
    5
    8
    'done'
    我们将上面函数中的print换成yield这个函数就变成了一个generator
    def fib(max):
        """generator打印斐波拉契数列"""
        n,a,b = 0,0,1
        while n<max:
            yield b
            a,b = b,a+b
            n+=1
        return 'done'
        
        >>> fib(5)
        <generator object fib at 0x000001DD86E77750>
        >>> f = fib(5)
        >>> next(f)
        1
        >>> next(f)
        1
        >>> next(f)
        2
        >>> next(f)
        3
        >>> next(f)
        5
        >>> next(f)
        Traceback (most recent call last):
          File "<pyshell#16>", line 1, in <module>
            next(f)
        StopIteration: done
    除第一次外每次调用这个函数都是从上次调用的yield语句之后开始执行
    上面这个generator我们发现最后无法捕获return的值,next到最后一个元素之后会产生一个StopIteration
    错误,我们捕获这个错误,最后return的就存在这个错误中:
    >>> while True:
            try:
                print(next(l))
            except StopIteration as e:
                print('Generator return val = ',e.value)
                break

            
        1
        1
        2
        3
        Generator return val =  done

 

posted @ 2020-06-13 17:37  pywhy  阅读(117)  评论(0编辑  收藏  举报