zoukankan      html  css  js  c++  java
  • Python3 笔记

    Ubuntu18.04 Python3环境

    默认python3已经安装了, 可能是安装其他应用的时候因为依赖关系安装的.

    安装pip3, 先sudo apt update 一下, apt-cache search python3-pip 看看有没有, 如果没有的话检查一下/etc/apt/sources.list 是否正确, 可以参考以下的source.list

    deb http://cn.archive.ubuntu.com/ubuntu/ bionic main restricted
    deb http://cn.archive.ubuntu.com/ubuntu/ bionic-updates main restricted
    deb http://cn.archive.ubuntu.com/ubuntu/ bionic universe
    deb http://cn.archive.ubuntu.com/ubuntu/ bionic-updates universe
    deb http://cn.archive.ubuntu.com/ubuntu/ bionic multiverse
    deb http://cn.archive.ubuntu.com/ubuntu/ bionic-updates multiverse
    deb http://cn.archive.ubuntu.com/ubuntu/ bionic-backports main restricted universe multiverse
    deb http://security.ubuntu.com/ubuntu bionic-security main restricted
    deb http://security.ubuntu.com/ubuntu bionic-security universe
    deb http://security.ubuntu.com/ubuntu bionic-security multiverse
    

    然后通过 sudo apt install python3-pip 安装

    常用的通过pip3安装的package: pymongo, 

    常用语法

    符号

    // 双斜杠表示地板除, 即先做除法/, 然后向下取整floor. 至少有一方是float时结果为float, 两方都是int时结果为int 

    合并两个Dictionary

    x = {'aa':1, 'bb':2, 'cc':3}
    y = {'aa':5, 'xx':6, 'yy':7}
    z = {**x, **y}
    x.update(y)
    print(x)
    # 输出
    {'aa': 5, 'bb': 2, 'cc': 3, 'xx': 6, 'yy': 7}
    {'aa': 5, 'bb': 2, 'cc': 3, 'xx': 6, 'yy': 7}
    

    两种方法都可以实现dictionary合并, 前者不会修改原先两个dictionary的值

    逻辑判断

    # 空, 非空
    if (x is None)
    if (not x is None)
    
    # dictionary是否包含某key
    if ('name' in x.keys())
    if (not 'name' in x.keys())
    

    字符串操作

    # 赋值时会自动合并
    y = 'Hello ' 'World'
    print(y)
    # substring, 截取从0到100(左边include, 右边exclude)的子串, slice方式不会报数组越界
    print(y[0:3])
    # Hel
    print(y[0:100])
    # Hello World
    print(y[-2:])
    # ld
    

    用%号做字符串赋值

    # 单个字符串
    msg = "he is %s ,his hobby is play" %"xiaoming"
    
    # 多个值
    msg = "he is %s ,his hobby is %s" %("xiaoming","play")
     
    # 百分号转义, 小数限位
    tpl="percent %.2f %%" %78.7658943256
    
    #键值对形式传字典
    tpl="i am %(name)s age %(age)d" %{"name":"小明","age":"18"}
    
    '''
    %c 字符及其ASCII码
    %s 字符串
    %d 有符号整数(十进制)
    %u 无符号整数(十进制)
    %o 无符号整数(八进制)
    %x 无符号整数(十六进制)
    %X 无符号整数(十六进制大写字符)
    %e 浮点数字(科学计数法)
    %E 浮点数字(科学计数法,用E代替e)
    %f 浮点数字(用小数点符号)
    %g 浮点数字(根据值的大小采用%e或%f)
    %G 浮点数字(类似于%g)
    %p 指针(用十六进制打印值的内存地址)
    %n 存储输出字符的数量放进参数列表的下一个变量中
    '''
    

    用format()做字符串赋值

    # 按顺序赋值
    tp1 = "i am {}, age {}, {}".format("seven", 18, 'alex')
    
    # 指定序号赋值
    tp3 = "i am {0}, age {1}, really {0}".format("seven", 18)
    
    # 指定名称赋值, 右侧结构为字典
    tp5 = "i am {name}, age {age}, really {name}".format(name="seven", age=18)
    
    # 指定类型赋值
    a1 = "numbers: {:b},{:o},{:d},{:x},{:X}, {:%},{:c}".format(15, 15, 15, 15, 15, 15.87623,65)
    
    # 指定 序号 + 类型
    a2 = "numbers: {0:b},{0:o},{0:d},{0:x},{0:X}, {0:%},{1:c}".format(15,65)
    
    # 指定 名称 + 类型
    a3 = "numbers: {num:b},{num:o},{num:d},{num:x},{num:X}, {num:%},{cc:c}".format(num=15,cc=65)
    
    ''' 可用类型
        ” 字符串类型 “的参数
            s,格式化字符串类型数据
            空白,未指定类型,则默认是None,同s
        “ 整数类型 ”的参数
            b,将10进制整数自动转换成2进制表示然后格式化
            c,将10进制整数自动转换为其对应的unicode字符
            d,十进制整数
            o,将10进制整数自动转换成8进制表示然后格式化;
            x,将10进制整数自动转换成16进制表示然后格式化(小写x)
            X,将10进制整数自动转换成16进制表示然后格式化(大写X)
        “ 浮点型或小数类型 ”的参数
            e, 转换为科学计数法(小写e)表示,然后格式化;
            E, 转换为科学计数法(大写E)表示,然后格式化;
            f , 转换为浮点型(默认小数点后保留6位)表示,然后格式化;
            F, 转换为浮点型(默认小数点后保留6位)表示,然后格式化;
            g, 自动在e和f中切换
            G, 自动在E和F中切换
            %,显示百分比(默认显示小数点后6位)
    '''
    

    .

    List, Tuple 和 Set

    tuple是不可变的, 用括号赋值(也可以不用)

    # tuple的赋值
    tup1 = 'str1',
    tup2 = ('str1',)
    tup3 = 'str1', 'str2'
    tup4 = ('str1', 'str2')
    tup5 = ([1,2,3], 'aa', 12345)

    list是可变的, list的操作与String很像, [a:b]实际上是对原数组的复制, 下面的代码就避免了操作原列表造成无限循环

    for w in words[:]:  # Loop over a slice copy of the entire list.
        if len(w) > 6:
            words.insert(0, w)
    

    list可以使用[[...]] 直接指定下标获得一个副本子序列, 里面的[...]也可以是表达式生成的list

    # 直接下标获取子序列copy
    iris_X_train = iris_X[[0,1,2,3]]
    # 通过list表达式指定
    iris_X_train = iris_X[indices[:-10]]
    

    .对list做运算, 都是直接对list内的元素作运算, 例如, 求得list中每一个元素的平方, 最后得到的也是同样元素个数的list

    # 求方差
    square_error = (iris_y_result - iris_y_test)**2
    

    .

    常用内置函数

    bin(x) 将一个整数转换为二进制值的字符串, 以 0b 开头(如果是负数则是 -0b)

    enumerate() 用于将一个可遍历的数据对象(如列表、元组或字符串)组合为一个索引序列, 同时列出数据和数据下标, 一般用在 for 循环当中, 可以指定下标开始值, 如 enumerate(seasons, start=1)

    id(object) 获取对象的全局唯一标识值. 注意, 如果两个对象的生命周期没有重叠, 可能会使用相同的对象id值

    input(prompt) 用于命令行执行中, 暂停并弹出输入提示, 返回值是输入的字符串

    len(x) 计算长度, 可以作用于序列或集合, a sequence (such as a string, bytes, tuple, list, or range) or a collection (such as a dictionary, set, or frozen set).

    list(iterable) 创建一个和iterable数组的元素一样次序也一样的list

    map(func, list) 接收一个函数 f 和一个 list,并通过把函数 f 依次作用在 list 的每个元素上,得到一个新的 list 并返回

    zip(*iterables) 合并参数中的多个iterable里的元素, 按原顺序, 不要求元素个数一致, 但是结果中只包含最短那个的个数

    常用模块

    HTTP请求. Requests模块

    使用手册 http://docs.python-requests.org/zh_CN/latest/api.html

    使用举例

    import requests
    
    def requestGet(url, encoding='UTF-8', tout=20, retries=10):
        count = 0
        while True:
            count += 1
            if (count > retries):
                print('Exceed retry limit')
                return None
            try:
                response = requests.get(url, timeout=tout)
                response.encoding = encoding
                return response.text
            except requests.ReadTimeout:
                print('ReadTimeout')
                continue
            except ConnectionError:
                print('ConnectionError')
                continue
            except requests.RequestException:
                print('RequestException')
                continue
    

    注意: 抓取GB2312网页时, encoding建议使用GB18030, 避免部分特殊文字乱码

    在Requests中保持session信息

    session = requests.session()
    
    # 然后就可以用session来进行各种http请求
    session.headers.update({
        'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:68.0) Gecko/20100101 Firefox/68.0',
        'Referer': config.base_url + '/default/',
        'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8'
    })
    #print(session.headers)
    #print(session.cookies.get_dict())
    
    post_data = {'id':user_name,'passwd': user_pass}
    rs = session.post(config.base_url + '/bbslogin1203.php', post_data, proxies=config.proxies)
    print(session.cookies.get_dict())
    

    在Reqeusts中使用代理

    如果使用socks5代理,需要安装pysocks (pip3 install pysocks)

    response = session.get(url, timeout=tout, proxies=dict(
        http='socks5://user:pass@host:port',
        https='socks5://user:pass@host:port'))
    

    各种代理的参数格式

    # SOCKS5 proxy for HTTP/HTTPS
    proxiesDict = {
        'http' : "socks5://1.2.3.4:1080",
        'https' : "socks5://1.2.3.4:1080"
    }
    
    # SOCKS4 proxy for HTTP/HTTPS
    proxiesDict = {
        'http' : "socks4://1.2.3.4:1080",
        'https' : "socks4://1.2.3.4:1080"
    }
    
    # HTTP proxy for HTTP/HTTPS
    proxiesDict = {
        'http' : "1.2.3.4:1080",
        'https' : "1.2.3.4:1080"
    }
    

      

    Mongodb 操作. Pymongo模块

    使用举例

    import pymongo
    
    # 连接mongodb
    client = pymongo.MongoClient('172.17.0.2', 27017)
    # 选择db
    db = client.db_1
    # 选择collection
    tb_user = db['user']
    # count
    total = tb_user.count_documents({})
    # select one
    dummy = tb_user.find_one({'_id': name})
    # select all, and sort
    allusers = tb_user.find().sort('posts', -1)
    # insert or save
    tb_user.save(user)
    

    Collection级别的操作

    # 创建索引
    collection_demo.create_index([('field1', pymongo.ASCENDING)])
    

    检查索引是否存在, 存在则删除索引

        indexes = board_col.list_indexes()
        for index in indexes:
            print(index)
            print(index['name'])
            if (index['name'] == 'author_text_created_at_-1'):
                board_col.drop_index('author_text_created_at_-1')
        # 创建联合索引
        board_col.create_index([('author', pymongo.TEXT),('created_at', pymongo.DESCENDING)])
    

      

    如果要在python中直接执行mongo 命令, 需要使用 eval(), 例如以下的语句用于将多个同构的collection合并到同一个collection

    for board in boards:
        tb_current = rbcommon.db['deb_' + str(board['_id'])]
        if (not tb_current is None):
            current_total = tb_current.find().count()
            print(str(board['_id']) + ', ' + board['name'] + ', ' + board['name2'] + ', ' + str(current_total))
            rbcommon.db.eval('db.deb_'+ str(board['_id']) +'.find({}).forEach(function(u) {db.deb_all.save(u);})')
    

    count_documents()的坑

    对于数据量很大的collection, 尽量不要使用这个方法, 因为这个方法实际上需要遍历所有documents, 会非常慢. 可以使用 estimated_document_count() 这个方法, 这个是从collection的metadata中读取的缓存的documents数量, 如果此时collection正在写入, 可能会与实际数量有出入.

    YAML配置文件读取

    import yaml
    
    # 获取当前文件的路径, 注意: 是common.py路径, 不带slash, 不是引用common的文件的路径, 
    # 可以用 os.path.realpath(__file__) 测试
    rootPath = os.path.dirname(__file__)
    print(rootPath)
    configPath = os.path.join(rootPath,'config.yml')
    print(configPath)
    
    with open(configPath, 'r') as ymlfile:
        cfg = yaml.load(ymlfile)
    
    # yaml会自动将长得像数字的值, 转换为数字类型. 下面是使用配置参数值的方式
    mongoclient = pymongo.MongoClient(cfg['mongo']['host'], cfg['mongo']['port'])
    db = mongoclient[cfg['mongo']['db']]
    tb_section = db['section']
    

    .

    常见问题

    循环中出现 pymongo.errors.CursorNotFound: cursor id xxx not found 错误

    默认mongo server维护连接的时间窗口是十分钟, 默认单次从 server获取数据是101条或者 大于1M小于16M的数据, 所以默认情况下如果循环中的某步在10分钟内未能处理完数据, 则抛出异常. 解决办法为使用no_cursor_timeout = True 参数

    allBoards = rbcommon.tb_board.find({}, no_cursor_timeout = True).sort('post_count', -1)
    for board in allBoards:
        # 0:through out mode, 1:increament mode
        readBoard(board)
    

    .

  • 相关阅读:
    nowcoderD Xieldy And His Password
    Codeforces681D Gifts by the List
    nowcoder80D applese的生日
    Codeforces961E Tufurama
    Codeforces957 Mahmoud and Ehab and yet another xor task
    nowcoder82E 无向图中的最短距离
    nowcoder82B 区间的连续段
    Codeforces903E Swapping Characters
    Codeforces614C Peter and Snow Blower
    Codeforces614D Skills
  • 原文地址:https://www.cnblogs.com/milton/p/10102367.html
Copyright © 2011-2022 走看看