• 19 python unit4 常用模块练习题&总结


     

     1、logging模块有几个日志级别?

    logging模块共有5个级别,分别是:
     DEBUG INFO WARNING ERROR CRITICAL
    logging的日志可以分为 debug(), info(), warning(), error(){ 美 /'ɛrɚ/ } and critical()5个级别

    2、请配置logging模块,单独在文件,屏幕。同时在屏幕和文件打印以下格式的日志

    #2017-10-18 15:56:26,613 - access - ERROR - account [1234] too many login attempts
    
    (1)仅将日志输出至屏幕
    a = 123
    # 打印输出
    import logging
    logging.basicConfig(format='%(asctime)s %(message)s', datefmt='%m/%d/%Y %I:%M:%S %p',level=logging.WARNING,filemode='a')
    logging.warning(f'{a}is when this event was logged.')

    (2)仅将日志输出至文件

    a = 123
    # 保存在文件中
    logging.basicConfig(filename='log.txt',format='%(asctime)s %(message)s', datefmt='%m/%d/%Y %I:%M:%S %p', level=logging.WARNING, filemode='a')
    logging.warning('how to use the python.')


    #将日志同时输出到屏幕和日志文件 import logging #logger提供了应用程序可以直接使用的接口; logger = logging.getLogger('access') logger.setLevel(level = logging.INFO) #handler将(logger创建的)日志记录发送到合适的目的输出; # FileHandler()输出至文件 file = logging.FileHandler("log.txt",encoding='utf-8') file.setLevel(logging.ERROR) # StreamHandler()输出至屏幕 console = logging.StreamHandler() console.setLevel(logging.ERROR) #增加指定的Handler logger.addHandler(file) logger.addHandler(console) #formatter决定日志记录的最终输出格式。 formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s') file.setFormatter(formatter) console.setFormatter(formatter) #logger.info("Start print log") logger.error("account [1234] too many login attempts") #logger.warning("Something maybe fail.") #logger.info("Finish")


    #---------------------------------------------------
    实例:
    #---------------------atm_user-------------------------
    logger_user = logging.getLogger('atm_user')
    # logger.setLevel()指定日志最低级别
    logger_user.setLevel(level = logging.DEBUG)
    #FileHandler()输出至文件
    handler_user = logging.FileHandler(settings.atm_user_path,encoding='utf-8')
    #指定被处理的信息最低级别 Handler.setLevel()
    handler_user.setLevel(logging.DEBUG)
    formatter = logging.Formatter('%(asctime)s--%(name)s--%(levelname)s--%(message)s')
    handler_user.setFormatter(formatter)
    logger_user.addHandler(handler_user)

    引用文件:
    logger.logger_user.debug(f"查看{account}信息 ")


    3、json、pickle、shelve三个区别是什么?

     首先,这三个模块都是序列化工具。
    
     1. json是所有语言的序列化工具,优点跨语言、体积小.只能序列化一些基本的数据类型。intstrlist	upledict
    
     pickle是python语言特有序列化工具,所有数据都能序列化。只能在python中使用,存储数据占空间大.
    
     shelve模块是一个简单的k,v(健值对)将内存数据通过文件持久化的模块,可以持久化任何pickle可支持的python数据格式。
    
     2. 使用方式,json和pickle用法一样,
    shelve是f =shelve.open('shelve_test')

    #-------------------------------------------------------------------------------------------------

    Python中两种序列化json和pickle区别
    序列化是把内存的数据类型转变为字符串(bytes类型)。
    json:用于字符串和Python数据类型之间进行转换
    pickle:用于Python特有类型(仅Python认识)和Python数据类型间进行转换。
    shelve:将内存数据通过文件持久化,支持任何pickle支持的数据格式。

    4、json的作用是什么?

     功能:序列化是指把内存里的数据类型转变成字符串,以使其能存储到硬盘或通过网络传输到远程,因为硬盘或网络传输时只能接受bytes(二进制)
    
    json,用于字符串和python数据类型间进行转换
    
    pickle,用于python特有的类型和python的数据类型间进行转换

    5、subprocess

    即允许你去创建一个新的进程让其执行另外的程序,并与它进行通信,获取标准的输入、标准输出、标准错误以及返回码等。 
     注意:使用这个模块之前要先引入该模块。
    
    
    我们经常需要通过Python去执行一条系统命令或脚本,系统的shell命令是独立于你的python进程之外的,
    每执行一条命令,就是发起一个新进程,通过python调用系统命令或脚本的模块在python2有os.system,
    除了os.system可以调用系统命令,,commands,popen2等也可以,比较乱,
    
    于是官方推出了subprocess,目地是提供统一的模块来实现对系统命令或脚本的调用
    
    三种执行命令的方法
    
    subprocess.run(*popenargs, input=None, timeout=None, check=False, **kwargs) #官方推荐
    
    subprocess.call(*popenargs, timeout=None, **kwargs) #跟上面实现的内容差不多,另一种写法
    
    subprocess.Popen() #上面各种方法的底层封装
    
    整个概念不理解!!!

    6、为什么要设计好目录结构?

    1.可读性高: 不熟悉这个项目的代码的人,一眼就能看懂目录结构,知道程序启动脚本是哪个,测试目录在哪儿,配置文件在哪儿等等。从而非常快速的了解这个项目。
    
    2.可维护性高: 定义好组织规则后,维护者就能很明确地知道,新增的哪个文件和代码应该放在什么目录之下。
    这个好处是,随着时间的推移,代码/配置的规模增加,项目结构不会混乱,仍然能够组织良好。

    7、打印出命令行的第一个参数。例如:

    python argument.py luffy
    打印出 luffy
    
    在脚本里面写入:
    from sys import argv
    script,name = argv
    print(name)
    
    在命令行里输入:
    
    先进入脚本所在目录
    D:> python argument.py luffy
    
    输出 luffy
    
    

    8、os/sys模块

    在当前目录下的D:/Pycharm/demo/LuFei/第二模块/第二章/练习题/argument.py 文件名:/argument.py

    '''
    import os
    
    # 获取路径名:os.path.dirname()
    # 获得绝对路径: os.path.abspath()
    
    BASE_DIR = os.path.abspath('argument.py') #文件的绝对路径
    BASE_DIR2 = os.path.dirname(os.path.abspath('argument.py'))
    BASE_DIR3 = os.path.dirname(os.path.dirname(os.path.abspath('argument.py')))
    BASE_DIR4 = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath('argument.py'))))
    
    print(BASE_DIR)
    print(BASE_DIR2)
    print(BASE_DIR3)
    print(BASE_DIR4)
    
    
    打印内容:
    D:PycharmdemoLuFei第二模块第二章练习题argument.py
    D:PycharmdemoLuFei第二模块第二章练习题
    D:PycharmdemoLuFei第二模块第二章
    D:PycharmdemoLuFei第二模块
    
    
    打印的内容是什么?
    os.path.dirname和os.path.abspath含义是什么?

    9、通过configparser模块完成以下功能:

    文件名my.cnf.ini
    
    [DEFAULT]
    
    [client]
    port = 3306
    socket = /data/mysql_3306/mysql.sock
    
    [mysqld]
    explicit_defaults_for_timestamp = true
    port = 3306
    socket = /data/mysql_3306/mysql.sock
    back_log = 80
    basedir = /usr/local/mysql
    tmpdir = /tmp
    datadir = /data/mysql_3306
    default-time-zone = '+8:00'
    -----------------------------------------
    
    import configparser
    config =configparser.ConfigParser() #初始化实例
    config.read('my.cnf.ini')#读取配置文件
    print(config.sections())#读取模块名到列表中,也就是[]中的内容
    
    print(config.default_section)
    >['client', 'mysqld']
    
    # 修改时区 default-time-zone = '+8:00' 为 校准的全球时间 +00:00
    config['mysqld']['default-time-zone'] = '+00:00'
    config.write(open('my.cnf.ini','w'))
    
    # 删除 explicit_defaults_for_timestamp = true
    config.remove_option('mysqld','explicit_defaults_for_timestamp = true')
    config.write(open('my.cnf.ini','w'))
    
    # 为DEFAULT增加一条 character-set-server = utf8
    config['DEFAULT']['character-set-server'] = 'utf8'
    config.write(open('my.cnf.ini','w'))
    
    ----------------------------------------------
    拓展:
    #读取指定sections内的所有key
    print('se_keys:',config.options('mysqld'))
    #获取指定sections的配置信息
    print(config.items('mysqld'))
    #在指定的sections中通过key找出value
    #通过get
    print(config.get('mysqld','back_log '))

    10、写一个6位随机验证码程序(使用random模块),要求验证码中至少包含一个数字、一个小写字母、一个大写字母.

    def choice():
        global ran1,ran2,ran3
        ran1 = random.randint(0,9) # randint()头尾都包括
        ran2 = chr(random.randint(65,90))# 大写
        ran3 = chr(random.randint(97,122))# 小写
    def random_num():
        global code
        code = ''
        for i in range(3):#生成为3位数的验证码
            choice()
            add = random.choice([ran1,ran2,ran3])
            code = ''.join([code,str(add)])
        return code
    import random
    choice()
    code2 =''.join([str(ran1),str(ran2),str(ran3)])
    random_num()
    print(''.join([code2,code]))
    
    拓展:数字,英文字母,标点符号
    print(''.join(random.sample(string.digits+string.punctuation+string.ascii_letters,6)))
    --------------------------------------------------------------- #使用 string模块 # 在大、小写、数字中随机返回6位数 import string,random s = ''.join(random.sample(string.ascii_letters + string.digits, 3)) ran1 = random.randint(0,9) # randint()头尾都包括 ran2 = chr(random.randint(65,90))# 大写 ran3 = chr(random.randint(97,122))# 小写 code =''.join([str(ran1),str(ran2),str(ran3)]) print(''.join([code,s]))

    11、利用正则表达式提取到 luffycity.com ,内容如下

    <!DOCTYPE html>
    <html lang="en">
    <head>
    <meta charset="UTF-8">
    <title>luffycity.com</title>
    </head>
    <body>
    </body>
    </html>
    
    import re
    f = open('index.html','r',encoding='utf-8')
    data = f.read()
    print(re.findall('luffycity.com',data))

    12、写一个用户登录验证程序

    ,文件如下 1234.json
    {"expire_date": "2021-01-01", "id": 1234, "status": 0, "pay_day": 22, "password": "abc"}
     
    用户名为json文件名,密码为 password。
    判断是否过期,与expire_date进行对比。
    登陆成功后,打印“登陆成功”,三次登陆失败,status值改为1,并且锁定账号。
    
    import json,time,datetime
    username = '1234.json'
    #首次登入将数据写入文件
    # data = {"expire_date": "2020-01-01", "id": 1234, "status": 0, "pay_day": 22, "password": "abc"}
    # with open('1234.json','r+',encoding='utf-8') as f:
    #     file = json.dump(data,f)
    with open('1234.json', 'r+', encoding='utf-8') as f2:
        file2 = json.load(f2)
    
    print('请登录用户名、密码进行验证:')
    
    count = 3
    while count > 0:
        user_name = input('name:>').strip()
        pass_word = input('password:>').strip()
        if file2['status'] == 1:
            print('该用户已锁定')
            exit()
        else:
            time_now = time.strftime('%Y-%m-%d')
            d1 = datetime.datetime.strptime(file2['expire_date'], '%Y-%m-%d')
            d2 = datetime.datetime.strptime(time_now, '%Y-%m-%d')
            if d1 > d2:
                if user_name == username:
                    if pass_word == file2['password']:
                        print('登录成功')
                        exit()
                    else:
                        count -= 1
                        print(f"您还有{count}次机会输入")
                        if count == 0:
                            file2['status'] = 1
                            with open('1234.json', 'w', encoding='utf-8') as f3:
                                json.dump(file2,f3)
                                break
    
                else:
                    print('用户名不存在:')
                    continue
    
            else:
                print('已过期')
                break

    13、把第12题三次验证的密码进行hashlib加密处理。

    即:json文件保存为md5的值,然后用md5的值进行验证。
    
    import hashlib
    file2 = {"expire_date": "2020-01-01", "id": 1234, "status": 0, "pay_day": 22, "password": "abc"}
    hash_pass = file2['password']
    m5 = hashlib.md5()
    pass_data= m5.update(b"hash_pass")
    #print(m5.digest(),type(m5.digest()))
    #print(m5.hexdigest())
    
    pass_word = input('>')
    pass_input = m5.update(b'pass_word')
    if pass_input == pass_data:
        print('nice')

    14、请用程序实现该转账行为

    14、最近luffy买了个tesla,通过转账的形式,并且支付了5%的手续费,tesla价格为75万。文件为json,
    请用程序实现该转账行为
    。 需求如下: . ├── account │ ├── luffy.json │ └── tesla.json └── bin └── start.py 当执行start.py时,出现交互窗口 ------- Luffy Bank --------- 1. 账户信息 2. 转账 选择1 账户信息 显示luffy的当前账户余额。 选择2 转账 直接扣掉75万和利息费用并且tesla账户增加75万 import json,os,sys #取出当前文件的目录dir,
    #当前文件父目录
    os.path.dirname(dir)
    print(__file__)
    dir = os.path.abspath(__file__)
    dir2 = os.path.dirname(os.path.dirname(dir))
    # 取出json文件的绝对路径
    file_path1 = dir2 + "\" + "account" + "\" + "luffy.json"
    file_path2 = dir2 + "\" + "account" + "\" + "tesla.json"
    print("""
    ------- Luffy Bank ---------
    1. 账户信息
    2. 转账
    """)
    while True:
    
        choice = input("""
    请选择如下序号:
    1. 账户信息
    2. 转账
    q.退出
    >
    """)
        #  此题前提在luffy 下存入100万
        with open(file_path1, 'r', encoding='utf-8') as f:
            balance = json.load(f)
        if choice == '1':
                print(f'当前余额:{balance}万')
                continue
        if choice == '2':
            balance = balance - balance*0.05 - 75
            tesla_balance = 75
            print(f"购买tesla共花费{balance - balance*0.05 - 75},tesla账户增加{tesla_balance}")
            with open(file_path2,'w',encoding='utf-8') as f2:
               json.dump(tesla_balance,f2)
            with open(file_path1, 'w', encoding='utf-8') as f3:
               json.dump(balance, f3)
               continue
    
        elif choice == 'q':
            exit()

    14.1、提现

    提现:
    对上题增加一个需求:提现。 目录结构如下
    
    .
    ├── account
    │ └── luffy.json
    ├── bin
    │ └── start.py
    └── core
    └── withdraw.py
    当执行start.py时,出现交互窗口
    
      ------- Luffy Bank ---------
      1. 账户信息
      2. 提现
    选择1 账户信息 显示luffy的当前账户余额和信用额度。
    选择2 提现 提现金额应小于等于信用额度,利息为5%,提现金额为用户自定义。
    
    import json,os,sys
    
    #取出当前文件的父目录,
    print(__file__)
    dir = os.path.abspath(__file__)
    dir2 = os.path.dirname(os.path.dirname(dir))
    # 取出json文件的绝对路径
    file_path1 = dir2 + "\" + "account" + "\" + "luffy.json"
    file_path2 = dir2 + "\" + "account" + "\" + "tesla.json"
    print("""
    ------- Luffy Bank ---------
    1. 账户信息
    2. 提现
    """)
    data = {'balance': 100, 'credit': 50}
    with open(file_path1, 'w', encoding='utf-8') as f:
        json.dump(data,f)
    while True:
    
        choice = input("""
    请选择如下序号:
    1. 账户信息
    2. 提现
    q.退出
    >
    """)
        #  此题前提在luffy 下存入data字典信息
        #data = {'balance': 100, 'credit': 50}
        with open(file_path1, 'r', encoding='utf-8') as f:
            #json.dump(data,f)
            balance = json.load(f)
        if choice == '1':
    
            print(f"当前余额:{balance['balance']}万,信用额度:{balance['credit']}万")
            continue
        if choice == '2':
            withdraw_money = int(input('请输入提现金额:').strip())
            if withdraw_money > balance['credit']:
                print(f"提现金额超过信用额度:{balance['credit']}万,请重新输入")
            else:
                balance['balance'] = balance['balance'] - withdraw_money - withdraw_money*0.05
                print(f"剩下余额{ balance['balance']}")
            with open(file_path1, 'w', encoding='utf-8') as f2:
               json.dump(balance, f2)
               continue
    
        elif choice == 'q':
            exit()

    14.2、加装饰器

    加登装饰器
    
    import json,os,sys
    
    #取出当前文件的父目录,
    print(__file__)
    dir = os.path.abspath(__file__)
    dir2 = os.path.dirname(os.path.dirname(dir))
    # 取出json文件的绝对路径
    file_path1 = dir2 + "\" + "account" + "\" + "luffy.json"
    file_path2 = dir2 + "\" + "account" + "\" + "tesla.json"
    global withdraw,transfer
    print("""
    ------- Luffy Bank ---------
    1. 账户信息
    2. 提现
    """)
    # data = {'balance': 100, 'credit': 50}
    # with open(file_path1, 'w', encoding='utf-8') as f:
    #     json.dump(data,f)
    user_status = False
    def login(fun):
        def inner(*args,**kwargs):
            user_name = 'xiao'
            pass_word = '123'
            global user_status
            if user_status == False:
                username = input('user:>').strip()
                password = input('password:>').strip()
                if username == user_name and pass_word == password:
                    print('welcome login...')
                    user_status = True
                else:
                    print('wrong username or passerword')
            if user_status == True:
                return fun(*args,**kwargs)
        return inner
    
    @login
    def transfer():
        tesla_balance = 75
        balance['balance'] = balance['balance'] - tesla_balance * 0.05 - 75
    
        print(f"购买tesla共花费{tesla_balance * 0.05 + 75},tesla账户增加{tesla_balance}")
        with open(file_path2, 'w', encoding='utf-8') as f2:
            json.dump(tesla_balance, f2)
        with open(file_path1, 'w', encoding='utf-8') as f3:
            json.dump(balance, f3)
    @login
    def withdraw():
        withdraw_money = int(input('请输入提现金额:').strip())
        if withdraw_money > balance['credit']:
            print(f"提现金额超过信用额度:{balance['credit']}万,请重新输入")
        else:
            balance['balance'] = balance['balance'] - withdraw_money - withdraw_money*0.05
            print(f"剩下余额{ balance['balance']}")
        with open(file_path1, 'w', encoding='utf-8') as f2:
           json.dump(balance, f2)
    
    ---------------------------------主函数-----------------------------------------
    while True:
    
        choice = input("""
    请选择如下序号:
    1. 账户信息
    2. 提现
    3.转账
    q.退出
    >
    """)
        #  此题前提在luffy 下存入data字典信息
        # data = {'balance': 100, 'credit': 50}
        with open(file_path1, 'r', encoding='utf-8') as f:
            # json.dump(data,f)
            balance = json.load(f)
        if choice == '1':
            print(f"当前余额:{balance['balance']}万,信用额度:{balance['credit']}万")
            continue
    
        if choice == '2':
            withdraw()
            continue
    
        if choice == '3':
            transfer()
            continue
        elif choice == 'q':
            exit()

     14.3、加日志功能

    加日志功能
    
    对第15题的用户转账、登录、提现操作均通过logging模块记录日志,日志文件位置如下
    
    .
    ├── account
    │ └── luffy.json
    ├── bin
    │ └── start.py
    └── core
    | └── withdraw.py
    └── logs
    └── bank.log
    
    import json,os,sys
    
    #取出当前文件的父目录,
    print(__file__)
    dir = os.path.abspath(__file__)
    dir2 = os.path.dirname(os.path.dirname(dir))
    # 取出json文件的绝对路径
    file_path1 = dir2 + "\" + "account" + "\" + "luffy.json"
    file_path2 = dir2 + "\" + "account" + "\" + "tesla.json"
    #bank.logs绝对路径
    file_path3 = os.path.dirname(dir)+"\" + "bank.log"
    
    global withdraw,transfer
    
    #日志
    # 将日志同时输出到屏幕和日志文件
    import logging
    #logger提供了应用程序可以直接使用的接口;
    logger = logging.getLogger('wed')
    logger.setLevel(level = logging.INFO)
    #handler将(logger创建的)日志记录发送到合适的目的输出;
    # FileHandler()输出至屏幕
    handler = logging.FileHandler(file_path3)
    handler.setLevel(logging.INFO)
    #formatter决定日志记录的最终输出格式。
    formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
    handler.setFormatter(formatter)
    # StreamHandler()输出至屏幕
    console = logging.StreamHandler()
    console.setLevel(logging.INFO)
    #增加指定的Handler
    logger.addHandler(handler)
    logger.addHandler(console)
    
    
    print("""
    ------- Luffy Bank ---------
    1. 账户信息
    2. 提现
    """)
    # data = {'balance': 100, 'credit': 50}
    # with open(file_path1, 'w', encoding='utf-8') as f:
    #     json.dump(data,f)
    user_status = False
    def login(fun):
        def inner(*args,**kwargs):
            user_name = 'xiao'
            pass_word = '123'
            global user_status
            if user_status == False:
                username = input('user:>').strip()
                password = input('password:>').strip()
                if username == user_name and pass_word == password:
                    logger.info('----登录-----')
                    print('welcome login...')
                    user_status = True
                else:
                    print('wrong username or passerword')
            if user_status == True:
                return fun(*args,**kwargs)
        return inner
    
    @login
    def transfer():
        tesla_balance = 75
        balance['balance'] = balance['balance'] - tesla_balance * 0.05 - 75
    
        print(f"购买tesla共花费{tesla_balance * 0.05 + 75},tesla账户增加{tesla_balance}")
        with open(file_path2, 'w', encoding='utf-8') as f2:
            json.dump(tesla_balance, f2)
        with open(file_path1, 'w', encoding='utf-8') as f3:
            json.dump(balance, f3)
    @login
    def withdraw():
        withdraw_money = int(input('请输入提现金额:').strip())
        if withdraw_money > balance['credit']:
            print(f"提现金额超过信用额度:{balance['credit']}万,请重新输入")
        else:
            balance['balance'] = balance['balance'] - withdraw_money - withdraw_money*0.05
            print(f"剩下余额{ balance['balance']}")
        with open(file_path1, 'w', encoding='utf-8') as f2:
           json.dump(balance, f2)
    
    
    while True:
    
        choice = input("""
    请选择如下序号:
    1. 账户信息
    2. 提现
    3.转账
    q.退出
    >
    """)
        #  此题前提在luffy 下存入data字典信息
        # data = {'balance': 100, 'credit': 50}
        with open(file_path1, 'r', encoding='utf-8') as f:
            # json.dump(data,f)
            balance = json.load(f)
        if choice == '1':
            logger.info('----显示账户信息-----')
            print(f"当前余额:{balance['balance']}万,信用额度:{balance['credit']}万")
            continue
    
        if choice == '2':
            logger.info('----提现-----')
            print()
            withdraw()
            continue
    
        if choice == '3':
            logger.info('----转账-----')
            transfer()
            continue
        elif choice == 'q':
            exit()
  • 相关阅读:
    【简●解】[AHOI2009]中国象棋
    【讲●解】KMP算法
    【简●解】POJ 1185,LG P2704【炮兵阵地】
    学习网站整理
    【讲●解】火车进出栈类问题 & 卡特兰数应用
    洛谷4556 [Vani有约会]雨天的尾巴
    BZOJ2212或洛谷3521 [POI2011]ROT-Tree Rotations
    洛谷1119 灾后重建
    洛谷1462(重题1951) 通往奥格瑞玛的道路(收费站_NOI导刊2009提高(2))
    BZOJ2721或洛谷1445 [Violet]樱花
  • 原文地址:https://www.cnblogs.com/foremostxl/p/9516729.html
Copyright © 2020-2023  润新知