zoukankan      html  css  js  c++  java
  • [ python ] 购物系统

    作业需求

    1. 购物系统,能够注册登录,用户第一次登录后,让用户输入金额,然后打印商品列表
    2. 允许用户根据商品编号购买商品
    3. 用户选择商品后,检测余额是否够,够就直接扣款,不够就提醒
    4. 购买完一件商品后打印购物清单及余额
    5. 可随时查看购物清单和退出
    6. 如果用户多次购买同一商品,必须合并商品数量和价格信息
    7. 用户下次登录时,可查看之前的消费记录

    流程图

    README

    1. 通过分析需求,使用面向过程和函数式编程的方式更好;
    2. 文件序列化通过 pickle实现永久存储;
    3. 每个用户信息用独立的数据文件来存储;
    4. 要求输入数字的地方只能输入正整数;
    5. 第二次购买的商品如果同第一次购买的相同,则在第一次商品信息上进行叠加。
    

    程序代码

    #!/usr/bin/python3
    # -*- coding: utf-8 -*-
    # Author: hkey
    
    import os, pickle
    
    
    def file_oper(file, mode, *args):
        '''
        通过pickle序列化持久存储数据信息
        :param file: 不同的用户生成不同的数据文件,文件名+'.db'
        :param mode: 对数据文件的操作,读取还是写入
        :param args: 需要写入的数据信息
        :return: 返回读取数据文件的信息
        '''
        if mode == 'wb':
            data = args[0]
            with open(file, mode) as f:
                pickle.dump(data, f)
        elif mode == 'rb':
            with open(file, mode) as f:
                data = pickle.load(f)
                return data
    
    
    def user(user, pwd, mode):
        '''
        用户注册及登录
        :param user: 用户输入的用户名
        :param pwd:  用户输入的密码
        :param mode: 注册还是登录
        :return: 登录成功,返回用户信息;登录失败,返回 None
        '''
        db_file = user + '.db'
        # 用户注册
        if mode == 'regist':
            if not os.path.isfile(db_file):
                user_info = {'name': user, 'passwd': pwd, 'stat': 0}
                file_oper(db_file, 'wb', user_info)
                print('33[32;1m注册成功.33[0m')
            else:
                print('33[31;1m错误:该用户已存在.33[0m')
        # 用户登录
        elif mode == 'login':
            if os.path.isfile(db_file):
                dict_user = file_oper(db_file, 'rb')
                if dict_user['name'] == user and dict_user['passwd'] == pwd:
                    print('33[32;1m登录成功.33[0m')
                    return dict_user
                else:
                    print('33[31;1m错误:用户名密码错误。33[0m')
            else:
                print('33[31;1m错误:该用户不存在.33[0m')
    
    
    def shopping(user_dict, list_goods):
        '''
        用户购物信息
        :param user_dict: 用户信息
        :param list_goods: 商品列表
        '''
    
        # 判断购物车内是否有商品
        if user_dict['shopping_car']:
            list_shopping = user_dict['shopping_car']
        else:
            list_shopping = []
        while True:
            print('33[32;1m商品列表33[0m'.center(50, '#'))
            for i, k in enumerate(list_goods):
                print('序号:%s	商品名:%s		价格:%s' % (i, k['name'], k['price']))
            choice = input('33[34;1m购买请输入商品序号[t 查看购物清单 q 退出]:33[0m').strip()
            if not choice: continue
            # 用户输入大小写 'q' 都是退出
            if choice.upper() == 'Q':
                break
            # 购买商品必须输入商品范围类的数字
            if choice.isdigit() and 0 <= int(choice) < len(list_goods):
                num = input('33[34;1m输入购买的数量:33[0m').strip()
                if num.isdigit():
                    num = int(num)
                else:
                    print('33[31;1m错误:数量必须是正整数.33[0m')
    
                # 获取用户输入的商品信息,并生成商品字典
                good = {'name': list_goods[int(choice)]['name'], 'num': num,
                        'total_prices': list_goods[int(choice)]['price'] * num}
                # 获取用户的余额
                money = user_dict['money']
                # 用户的余额 - 商品的总价
                res_money = money - good['total_prices']
                if res_money >= 0:
                    # 这里目前没有想到好的处理办法,只能使用标记来做判断
                    # 默认 flag 为 True,因为用户一次只能购买一件商品,如果用户购买的是重复的商品,就将购买过的商品信息合并,
                    # 然后将 flag 设置为 False
                    flag = True
                    for i in list_shopping:
                        if good['name'] == i['name']:
                            i['num'] += good['num']
                            i['total_prices'] += good['total_prices']
                            flag = False
                    # 当flag = True 说明用户没有购买重复的商品,添加新商品到购物清单;反之则购买了重复的商品 flag = False
                    if flag:
                        list_shopping.append(good)
                    print('33[32;1m购买成功!33[0m
    ')
                    print('33[32;1m购物清单33[0m'.center(50, '#'))
                    for i in list_shopping:
                        print('商品名:%s	数量:%s	总价:%d元' % (i['name'], i['num'], i['total_prices']))
                    print('33[33;1m您的余额为:%d元33[0m' % res_money)
                    print('##########################################
    ')
                    # 修改购物后的用户余额信息
                    user_dict['money'] = res_money
                    # 修改购物清单信息
                    user_dict['shopping_car'] = list_shopping
                    # 将修改后的数据写入数据文件
                    file_oper(user_dict['name'] + '.db', 'wb', user_dict)
                else:
                    print('33[31;1m错误:商品总价为:%d元,您的余额为:%d元,购物失败.33[0m' % (good['total_prices'], money))
    
            elif choice.upper() == 'T':
                print('33[32;1m购物清单33[0m'.center(50, '#'))
                for i in list_shopping:
                    print('商品名:%s	数量:%s	总价:%d元' % (i['name'], i['num'], i['total_prices']))
                print('33[33;1m您的余额为:%d元33[0m' % user_dict['money'])
                print('##########################################
    ')
                any = input('33[34;1m任意键返回商品列表33[0m').strip()
                continue
            else:
                print('33[31;1m错误:输入商品序号错误。33[0m')
    
    
    def start(list_goods):
        while True:
            print('1. 注册
    '
                  '2. 登录
    '
                  '3. 退出')
            choice = input('>>>').strip()
            if not choice: continue
            if choice.isdigit() and 0 < int(choice) < 4:
                if choice == '1':
                    username = input('33[34;1m输入用户名:33[0m').strip()
                    password = input('33[34;1m输入密码:33[0m').strip()
                    user(username, password, 'regist')
    
                elif choice == '2':
                    username = input('33[34;1m输入用户名:33[0m').strip()
                    password = input('33[34;1m输入密码:33[0m').strip()
                    user_dict = user(username, password, 'login')
                    # 当 user(username, password, 'login') 返回 None表示登录失败
                    if user_dict is None:
                        continue
                    # user_dict['stat'] = 0 表示用户第一次登录,user_dict['stat'] 非零则表示用户多次登录
                    if user_dict['stat'] == 0:
                        money = input('33[34;1m首次登录,请输入充值金额:33[0m').strip()
                        if money.isdigit():  # 这里无法判断小数类型
                            user_dict['money'] = int(money)
                            # 第一次登录设置成功金额后,将 stat 设置为非零
                            user_dict['stat'] = 1
                            user_dict['shopping_car'] = []
                            print('33[32;1m恭喜:充值成功!33[0m')
                            shopping(user_dict, list_goods)
    
                        else:
                            print('33[31;1m错误:金额只能是正整数!33[0m')
                    # user_dict['stat'] = 0 表示用户第一次登录,user_dict['stat'] 非零则表示用户多次登录
                    else:
                        shopping(user_dict, list_goods)
                elif choice == '3':
                    break
            else:
                print('33[31;1m错误:序号输入错误.33[0m')
    
    
    if __name__ == '__main__':
        # 商品列表
        list_goods = [
            {'name': '苹果', 'price': 10},
            {'name': '鸭梨', 'price': 20},
            {'name': '芒果', 'price': 30},
        ]
    
        start(list_goods)
    shopping.py

    部分运行截图:

    图1:

    图2:

     

    图3:

    图4:

  • 相关阅读:
    HDU 6043
    HDU 6033
    HDU 6041
    HDU 6050
    HDU 6053
    HDU 6055
    HDU 6045
    HDU 6044
    HDU 6040
    ZUFE 1035 字符宽度编码(字符串)
  • 原文地址:https://www.cnblogs.com/hukey/p/9665707.html
Copyright © 2011-2022 走看看