Python实现一个购物车系统

架构

  • shopcar

    • admin.py > 管理类

      存储用户字典 用户id作为键 用户对象作为值

      注册 登录 购物车添加商品 购物车删除商品 结算购物车 注销

    • goods.py > 商品类

      商品属性:商品名称 商品价格 商品数量

    • shopcar.py > 购物车类

      存储商品字典

      商品对象作为键 商品数量作为值

    • storage.py > 仓库类

      存储商品列表

      列表中的元素是商品对象

    • user.py > 用户类

      用户属性:用户id 用户名 用户密码 购物车 状态(登录与否)

    • main.py > 入口

      调用管理类的功能进行界面操作

    • resources > 数据库

      存储商品信息 用户信息

构造有点复杂 涉及大量的文件操作 出错率很高 先实现几个简单的模块吧

代码实现

goods.py

class Goods:
    # 限制动态添加属性
    __slots__ = ("gname", "gprice", "gnum")
​
    def __init__(self, gname, gprice, gnum):
        self.gname = gname
        self.gprice = gprice
        self.gnum = gnum
​
    def __str__(self):
        return f'商品名:{self.gname}, 商品价格:{self.gprice}, 商品数量:{self.gnum}'
​
    # __str__显示给用户
    # __repr__显示给开发人员
    # 定义__repr__
    __repr__ = __str__

user.py

class User:
    
    __slots__ = ("uid", "uname", "upassword", "ushopcar", "login")
    
    def __init__(self, uid, uname, upassword, ushopcar):
        self.uid = uid
        self.uname = uname
        self.upassword = upassword
        self.ushopcar = ushopcar
        self.islogin = False
    
    def __str__(self):
        return f'用户id:{self.uid}\n用户名:{self.uname}\n用户登录状态:{self.islogin}'
    
    __repr__ = __str__

shopcar.py

class ShoppingCar:
    # 元组只有一个元素需要添加,
    __slots__ = ("goods_dict",)
    
    def __init__(self):
        self.goods_dict = {}
        
    def __str__(self):
        return f'购物车:{self.goods_dict}'
    
    __repr__ = __str__

单例模式

storage.py

import os
import pickle
from goods import Goods
​
path = 'resources/goods_list.txt'
​
​
# 单例装饰器
def singleton(cls):
    instance = None
​
    def get_instance(*args, **kwargs):
        nonlocal instance
        if not instance:
            instance = cls(*args, **kwargs)
        return instance
    return get_instance
​
​
# 限制只能有一个仓库实例
@singleton
class Storage:
​
    __slots__ = ("goods_list",)
​
    def __init__(self):
        self.goods_list = None
        self.load_goods()
​
    def load_goods(self):
        if not os.path.exists(path):
            self.goods_list = []
            names_list = ['iPhone14', 'iPhone13', 'iPhone12', 'iPhone11']
            prices_list = [8000, 7000, 6000, 5000]
            nums_list = [50, 40, 30, 20]
            for i in range(len(names_list)):
                goods = Goods(names_list[i], prices_list[i], nums_list[i])
                self.goods_list.append(goods)
            self.save_goods()
        else:
            self.load_goods()
​
    def save_goods(self):
        with open(path, 'wb') as f:
            pickle.dump(self.goods_list, f)
​
    def load_goods(self):
        with open(path, 'rb') as f:
            self.goods_list = pickle.load(f)

核心模块

admin.py

from user import User
import os
import pickle
import uuid
from shopcar import ShoppingCar
from storage import Storage
from goods import Goods
​
path = 'resources/user.txt'
​
​
class Admin:
​
    __slots__ = ("user_dict",)
​
    def __init__(self):
        self.user_dict = None
        self.load_users()
​
    def load_users(self):
        if os.path.exists(path):
            with open(path, 'rb') as f:
                self.user_dict = pickle.load(f)
        else:
            self.user_dict = {}
​
    def save_users(self):
        with open(path, 'wb') as f:
            pickle.dump(self.user_dict, f)
​
    @property
    def __get_uid(self):
        while 1:
            # 使用uuid模块随机生成用户的uid
            uid = str(uuid.uuid4()).split('-')[1]
            # 确保uid唯一
            if uid not in self.user_dict:
                print(f'当前用户的uid是{uid}')
                return uid
​
    def user_register(self):
        uid = self.__get_uid
        name = input('请输入用户名:')
        password = input('请输入密码:')
        shopcar = ShoppingCar()
        user = User(uid, name, password, shopcar)
        self.user_dict[uid] = user
        # 保存数据
        self.save_users()
        print('注册成功')
​
    def user_login(self):
        uid = input('请输入用户uid:')
        if uid not in self.user_dict:
            print('用户不存在 请先注册')
            return
        user = self.user_dict[uid]
        if user.islogin:
            print('用户已登录')
            return user
        cnt = 0
        while 1:
            cnt += 1
            # 三次输入机会
            if cnt > 3:
                print('输入错误次数过多 禁止登录')
                return
            name = input('请输入用户名:')
            password = input('请输入密码:')
            if name == user.uname and password == user.upassword:
                print('登录成功')
                # 设置登录状态
                user.islogin = True
                self.user_dict[user.uid] = user
                self.save_users()
                # 返回登录后的用户
                return user
            else:
                print('用户名或密码错误')
​
    def add_goods(self):
        '''
        同步仓库和购物车的数据
        '''
        user = self.user_login()
        if not user:
            print('您还未登录 请先登录')
            return
        # 添加商品会减少库存
        storage = Storage()
        print('商品列表如下:')
        # 库存中的商品对象
        for i in range(len(storage.goods_list)):
            print(f'{i}.{storage.goods_list[i]}')
        i = input('请输入要购买的商品编号:')
        if i.isdigit():
            i = int(i)
            if i in range(len(storage.goods_list)):
                goods = storage.goods_list[i]
                n = int(input(f'请输入要购买的{goods.gname}商品数量:'))
                if n <= 0:
                    print('购买数量不能≤0')
                else:
                    while n > goods.gnum:
                        n = int(input(f'剩余商品数量为{goods.gnum}, 库存不足\n请重新输入购买数量:'))
                    else:
                        # 购物车中的商品对象
                        ugoods = Goods(goods.gname, goods.gprice, n)
                        if ugoods in user.ushopcar.goods_dict:
                            user.ushopcar.goods_dict[ugoods] += n
                        else:
                            user.ushopcar.goods_dict[ugoods] = n
                        storage.goods_list[i].gnum -= n
                        storage.save_goods()
                        # 更新用户信息
                        self.user_dict[user.uid] = user
                        self.save_users()
                        print(f'{goods.gname}添加成功')
            else:
                print('暂无该商品')
        else:
            print('商品编号输入有误')
            return
​
    def del_goods(self):
        user = self.user_login()
        if not user:
            print('您还未登录 请先登录')
            return
        print('您的购物车如下:')
        for goods in user.ushopcar.goods_dict.keys():
            print(goods)
        gname = input('请输入要删除的商品名:')
#       购物车商品    仓库商品
        car_goods, sto_goods = None, None
        for goods in user.ushopcar.goods_dict.keys():
            if goods.gname == gname:
                car_goods = goods
                break
        else:
            print(f'{gname}商品不在您的购物车中')
            return
        storage = Storage()
        for goods in storage.goods_list:
            if goods.gname == gname:
                sto_goods = goods
                break
        n = int(input(f'请输入要删除的商品{gname}数量'))
        if n >= car_goods.gnum:
            user.ushopcar.goods_dict.pop(car_goods)
            sto_goods.gnum += n
        else:
            car_goods.gnum -= n
            user.ushopcar.goods_dict[car_goods] = car_goods.gnum
            sto_goods.gnum += n
        # 更新仓库信息
        storage.goods_list[storage.goods_list.index(sto_goods)] = sto_goods
        storage.save_goods()
        # 更新购物车信息
        self.user_dict[user.uid] = user
        self.save_users()
        print(f'{gname}删除成功')
​
    def buy_goods(self):
        user = self.user_login()
        if not user:
            print('您还未登录 请先登录')
            return
        total_price = 0
        for goods, num in user.ushopcar.goods_dict.items():
            total_price += goods.gprice * num
        print(f'总价格是¥{total_price}')
        # 清空用户购物车
        user.ushopcar.goods_dict.clear()
        self.user_dict[user.uid] = user
        self.save_users()
        print('结算成功')
​
    def user_logout(self):
        user = self.user_login()
        if user:
            user.islogin = False
            self.user_dict[user.uid] = user
            self.save_users()
            print('退出登录成功')
        else:
            print('用户读取失败')

main.py

from admin import Admin
​
​
def main():
    admin = Admin()
    print('欢迎登录千锋购物系统'.center(30, '*'))
    print('''
    1.用户注册
    2.用户登录
    3.购物车添加商品
    4.购物车删除商品
    5.结算购物车中的商品
    6.注销用户
    7.退出系统
    ''')
    while 1:
        op = input('请选择您想进行的操作:')
        if op == '1':
            admin.user_register()
        elif op == '2':
            admin.user_login()
        elif op == '3':
            admin.add_goods()
        elif op == '4':
            admin.del_goods()
        elif op == '5':
            admin.buy_goods()
        elif op == '6':
            admin.user_logout()
        elif op == '7':
            print('退出成功')
            exit()
        else:
            print('当前操作不合法')


版权声明:本文为qq_45580637原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。