【愚公系列】《Python网络爬虫从入门到精通》063-项目实战电商数据侦探(主窗体的数据展示)

news2025/4/24 7:06:35

🌟【技术大咖愚公搬代码:全栈专家的成长之路,你关注的宝藏博主在这里!】🌟

📣开发者圈持续输出高质量干货的"愚公精神"践行者——全网百万开发者都在追更的顶级技术博主!

👉 江湖人称"愚公搬代码",用七年如一日的精神深耕技术领域,以"挖山不止"的毅力为开发者们搬开知识道路上的重重阻碍!

💎【行业认证·权威头衔】
✔ 华为云天团核心成员:特约编辑/云享专家/开发者专家/产品云测专家
✔ 开发者社区全满贯:CSDN博客&商业化双料专家/阿里云签约作者/腾讯云内容共创官/掘金&亚马逊&51CTO顶级博主
✔ 技术生态共建先锋:横跨鸿蒙、云计算、AI等前沿领域的技术布道者

🏆【荣誉殿堂】
🎖 连续三年蝉联"华为云十佳博主"(2022-2024)
🎖 双冠加冕CSDN"年度博客之星TOP2"(2022&2023)
🎖 十余个技术社区年度杰出贡献奖得主

📚【知识宝库】
覆盖全栈技术矩阵:
◾ 编程语言:.NET/Java/Python/Go/Node…
◾ 移动生态:HarmonyOS/iOS/Android/小程序
◾ 前沿领域:物联网/网络安全/大数据/AI/元宇宙
◾ 游戏开发:Unity3D引擎深度解析
每日更新硬核教程+实战案例,助你打通技术任督二脉!

💌【特别邀请】
正在构建技术人脉圈的你:
👍 如果这篇推文让你收获满满,点击"在看"传递技术火炬
💬 在评论区留下你最想学习的技术方向
⭐ 点击"收藏"建立你的私人知识库
🔔 关注公众号获取独家技术内参
✨与其仰望大神,不如成为大神!关注"愚公搬代码",让坚持的力量带你穿越技术迷雾,见证从量变到质变的奇迹!✨ |

文章目录

  • 🚀前言
  • 🚀一、主窗体的数据展示
    • 🔎1.显示前10名热卖榜图文信息
      • 🦋1.1 步骤概述
      • 🦋1.2 具体步骤
        • ☀️(1) 导入自定义模块并创建对象
        • ☀️(2) 获取热卖排行榜信息并插入数据库
        • ☀️(3) 创建 `show_top10()` 方法显示图文信息
        • ☀️(4) 创建用于显示商品图片的 `QLabel` 控件
        • ☀️(5) 创建用于显示好评率的 `QLabel` 控件
        • ☀️(6) 创建用于显示商品名称的 `QLabel` 控件
        • ☀️(7) 创建用于显示商品价格的 `QLabel` 控件
        • ☀️(8) 创建关注商品按钮 `QPushButton`
        • ☀️(9) 将动态创建的布局添加到网格布局
        • ☀️(10) 在主程序入口调用 `show_top10()` 方法
      • 🦋1.3 运行效果
    • 🔎2.显示关注商品列表
      • 🦋2.1 确认关注
      • 🦋2.2 取消关注
    • 🔎3.显示商品分类比例饼图
      • 🦋3.1 创建 `chart.py` 文件
      • 🦋3.2 创建 `pie_chart()` 方法显示饼图
      • 🦋3.3 在 `show_window.py` 中导入自定义饼图类
      • 🦋3.4 排除重复商品名称并计算分类比例
      • 🦋3.5 计算其他商品分类的占比
      • 🦋3.6 创建饼图并显示
      • 🦋3.7 调用 `show_classification()` 方法显示饼图
      • 🦋3.8 运行并显示饼图


🚀前言

在之前的内容中,我们已经完成了电商数据侦探项目的多个环节,包括需求分析、系统设计、UI设计以及数据的爬取与存储。现在,我们进入了项目的下一阶段——主窗体的数据展示

数据展示是爬虫项目中至关重要的一步,因为它直接影响到用户如何理解和利用爬取到的数据。一个清晰、直观的数据展示界面不仅能提升用户体验,还能帮助用户更有效地分析和决策。在本篇文章中,我们将重点讨论如何将爬取到的电商数据呈现给用户,并为后续的数据分析提供方便。

具体内容包括:

  1. 数据展示的设计原则:如何设计一个直观的界面,确保用户可以清晰地看到爬取的数据,避免信息过载。
  2. 商品信息展示:将商品的关键信息(如名称、价格、评分、销量等)通过表格、列表或图形化的方式展示,确保用户能够轻松浏览。
  3. 价格走势图展示:通过图表的方式展示商品的价格波动情况,帮助用户分析商品价格的走势和规律。
  4. 用户评价展示:展示商品的用户评论,包括评分、评论内容等,便于用户了解其他消费者的购买体验。
  5. 交互与更新:实现动态数据展示,支持用户刷新、筛选或排序数据,以便于用户根据不同需求查看信息。
  6. 数据的可视化展示:使用图表或图形方式进一步呈现数据趋势,例如价格变化趋势图、热销商品排名图等,提升数据分析的可视化效果。

通过本篇文章的学习,你将学会如何将爬取到的电商数据通过精心设计的主窗体展现给用户,使数据不仅仅是冷冰冰的数字,而是充满价值的信息和见解。这将大大提升你爬虫项目的实用性和商业价值。

🚀一、主窗体的数据展示

在实现主窗体数据展示时,需要考虑到主窗体中有三个区域:

  1. 显示前10名热卖榜图文信息
  2. 显示关注商品列表
  3. 显示商品分类饼图

首先,我们需要动态创建“显示前10名热卖榜图文信息”的布局,并实现商品的关注功能。接着,我们将单独创建一个图表文件来显示商品分类比例的饼图。最后,使用数据库操作文件将所有数据显示在主窗体中。

🔎1.显示前10名热卖榜图文信息

🦋1.1 步骤概述

  1. 导入相关自定义模块:首先,需要导入自定义数据库操作类和爬虫类。
  2. 获取热卖榜信息并插入数据库:爬取热卖榜信息并将其保存至数据库中。
  3. 从数据库中提取数据:从数据库中提取前10名热卖榜信息。
  4. 动态创建布局:根据提取的数据显示图文信息。
  5. 显示热卖榜图文信息:将图文信息展示在主窗体上。

🦋1.2 具体步骤

☀️(1) 导入自定义模块并创建对象

首先,在 show_window.py 文件中导入数据库操作类和爬虫类,并创建相应的对象。代码如下:

from mysql import MySQL
from crawl import Crawl

mycrawl = Crawl()  # 创建爬虫类对象
mysql = MySQL()    # 创建数据库对象

# 连接数据库
sql = mysql.connection_sql()

# 创建数据库游标
cur = sql.cursor()
☀️(2) 获取热卖排行榜信息并插入数据库

Main 类的 __init__() 方法中,获取热卖排行榜信息与商品价格,并将数据保存到数据库中。代码如下:

# 获取热卖排行榜信息
id_str = mycrawl.get_rankings_json('https://ch.jd.com/hotsale2?cateid=686')
rankings_list = mycrawl.get_price(id_str)  # 获取价格,然后在该方法中将所有数据保存至列表并返回
mysql.insert_ranking(cur, rankings_list, 'jd_ranking')  # 将数据插入数据库
☀️(3) 创建 show_top10() 方法显示图文信息

Main 类中,创建 show_top10() 方法来显示前10名热卖榜图文信息。在该方法中,首先创建外层布局 QWidget 控件。代码如下:

def show_top10(self):
    top_10_info = mysql.query_top10_info(cur)  # 查询排行数据表前10名商品名称,价格,好评率
    # 行数标记
    i = -1
    for n in range(10):
        # x 确定每行显示的个数 0,1,2 每行2个
        x = n % 2
        # 当x为0的时候设置换行 行数+1
        if x == 0:
            i += 1
        # 创建布局
        self.widget = QtWidgets.QWidget()
        # 给布局命名
        self.widget.setObjectName("widget" + str(n))
        # 设置布局样式
        self.widget.setStyleSheet('QWidget#' + "widget" + str(
            n) + "{border:2px solid rgb(175, 175, 175);background-color: rgb(255, 255, 255);}")
☀️(4) 创建用于显示商品图片的 QLabel 控件

依次添加代码,在 QWidget 控件中创建用于显示商品图片的 QLabel 控件。代码如下:

# 创建个Qlabel控件用于显示图片 设置控件在QWidget中
self.label = QtWidgets.QLabel(self.widget)
# 设置大小
self.label.setGeometry(QtCore.QRect(15, 15, 160, 160))
# 设置要显示的图片
self.label.setPixmap(QtGui.QPixmap('img_download/' + str(n) + '.jpg'))
# 图片显示方式 让图片适应QLabel的大小
self.label.setScaledContents(True)
# 给显示图片的label控件命名
self.label.setObjectName("img_download" + str(n))
# 设置控件样式
self.label.setStyleSheet('border:2px solid rgb(175, 175, 175);')
☀️(5) 创建用于显示好评率的 QLabel 控件

添加代码,在 QWidget 控件中创建用于显示好评率的 QLabel 控件。代码如下:

# 显示好评的Label控件
self.label_good = QtWidgets.QLabel(self.widget)
# 给好评率控件命名
self.label_good.setObjectName("good" + str(n))
self.label_good.setGeometry(QtCore.QRect(24, 180, 141, 40))  # 设置控件位置及大小
# 设置控件样式,边框与颜色
self.label_good.setStyleSheet("border: 2px solid rgb(255, 148, 61);color: rgb(255, 148, 61);")
self.label_good.setAlignment(QtCore.Qt.AlignCenter)  # 控件内文字居中显示
self.label_good.setText('好评率' + top_10_info[n][2])  # 显示好评率的文字
font = QtGui.QFont()    # 创建字体对象
font.setPointSize(18)   # 设置字体大小
font.setBold(True)     # 开启粗体属性
font.setWeight(75)     # 设置文字粗细
self.label_good.setFont(font) # 设置字体
☀️(6) 创建用于显示商品名称的 QLabel 控件

依次添加代码,在 QWidget 控件中创建用于显示商品名称的 QLabel 控件。代码如下:

# 显示名称的Label控件
self.label_name = QtWidgets.QLabel(self.widget)
# 给显示名称控件命名
self.label_name.setObjectName("good" + str(n))
# 设置控件位置及大小
self.label_name.setGeometry(QtCore.QRect(185, 30, 228, 80))
self.label_name.setText(top_10_info[n][0])  # 设置显示名称的文字
# 左上角为主显示文字
self.label_name.setAlignment(QtCore.Qt.AlignLeft | QtCore.Qt.AlignTop)
self.label_name.setWordWrap(True)  # 设置文字自动换行
font = QtGui.QFont()  # 创建字体对象
font.setPointSize(9)  # 设置字体大小
font.setBold(True)    # 开启粗体属性
font.setWeight(75)    # 设置文字粗细
self.label_name.setFont(font)   # 设置字体
☀️(7) 创建用于显示商品价格的 QLabel 控件

依次添加代码,在 QWidget 控件中创建用于显示商品价格的 QLabel 控件。代码如下:

# 显示价格的Label控件
self.label_price = QtWidgets.QLabel(self.widget)
# 给显示价格控件命名
self.label_price.setObjectName("price" + str(n))
# 设置控件位置及大小
self.label_price.setGeometry(QtCore.QRect(200, 80, 228, 80))
# 设置控件样式
self.label_price.setStyleSheet("color: rgb(255, 0, 0);")
self.label_price.setText('¥' + top_10_info[n][1])  # 设置显示的价格文字
font = QtGui.QFont()    # 创建字体对象
font.setPointSize(20)   # 设置字体大小
font.setBold(True)     # 开启粗体属性
font.setWeight(75)     # 设置文字粗细
self.label_price.setFont(font)   # 设置字体
☀️(8) 创建关注商品按钮 QPushButton

依次添加代码,在 QWidget 控件中创建用于显示关注商品的 QPushButton 控件。代码如下:

# 显示关注按钮控件
self.pushButton = QtWidgets.QPushButton(self.widget)
# 给显示价格控件命名
self.pushButton.setObjectName(str(n))
# 设置控件位置及大小
self.pushButton.setGeometry(QtCore.QRect(300, 160, 100, 50))
font = QtGui.QFont()     # 创建字体对象
font.setFamily("楷体")   # 设置字体
font.setPointSize(18)    # 设置字体大小
font.setBold(True)      # 开启粗体属性
font.setWeight(75)      # 设置文字粗细
self.pushButton.setFont(font)   # 设置字体
# 设置关注按钮控件样式
self.pushButton.setStyleSheet("background-color: rgb(223, 48, 51);color: rgb(255, 255, 255);")
self.pushButton.setText('关注')   # 设置关注按钮显示的文字
# 注册关注按钮信号槽
self.pushButton.clicked.connect(self.attention_btn)
☀️(9) 将动态创建的布局添加到网格布局

将动态创建的 widget 布局添加到网格布局中,并设置滚动条的高度为动态高度。代码如下:

    # 把动态创建的widegt布局添加到gridLayout中 i,x分别代表:行数以及每行的个数
    self.gridLayout.addWidget(self.widget, i, x)
    # 设置高度为动态高度根据 行数确定高度 每行300
self.scrollAreaWidgetContents.setMinimumHeight((i+1) * 240)
# 设置网格布局控件动态高度
self.gridLayoutWidget.setGeometry(QtCore.QRect(0, 0, 850, ((i+1) * 240)))
☀️(10) 在主程序入口调用 show_top10() 方法

最后,在主程序入口显示主窗体时,调用 show_top10() 方法。代码如下:

main.show_top10()

🦋1.3 运行效果

运行 show_window.py 文件后,主窗体会显示热卖商品前10名的图文信息,如图所示。由于热卖商品排行榜数据会自动更新,主窗体每次显示的信息可能会有所变化。
在这里插入图片描述

🔎2.显示关注商品列表

在实现显示关注商品列表时,需要首先实现热卖商品的关注功能。关注按钮需要设置关注事件,单击商品的关注按钮时会弹出一个确认关注的小窗体,以避免误操作。确认关注后,需要将商品信息保存至数据库,并将关注的商品名称显示在关注商品列表中。同时,取消关注功能也需要实现,单击关注商品列表中的商品名称时,会弹出确认取消关注的小窗体进行确认。

🦋2.1 确认关注

  1. 窗体设计

    • 打开Qt Designer工具,设置窗体的最大尺寸与最小尺寸为400x200,并移除默认的状态栏和菜单栏。
    • 在窗体中拖入一个QLineEdit控件用于显示需要关注商品的名称,拖入两个QPushButton控件分别用于确认关注与取消关注。
    • 窗体设计完成后,保存为attention_window.ui文件,使用pyuic工具将其转换为attention_window.py文件。
      在这里插入图片描述
  2. 代码实现

    • attention_window.py文件中,将默认生成的Ui_MainWindow类修改为Attention_MainWindow
    • 打开show_window.py文件,导入关注窗体文件中的UI类,并定义显示提示对话框的方法:
    from attention_window import Attention_MainWindow  # 导入关注窗体文件中的UI类
    attention_info = ''  # 关注商品信息
    def messageDialog(title, message):
        msg_box = QtWidgets.QMessageBox(QtWidgets.QMessageBox.Warning, title, message)
        msg_box.exec()
    
  3. 关注按钮事件

    • 在Main类中,创建attention_btn()方法处理关注按钮的事件:
    # 关注按钮事件
    def attention_btn(self):
        # 获取信号源 点击的按钮
        sender = self.gridLayout.sender()
        global attention_info
        # 因为创建关注按钮对象名称是以0为起始,最后一个关注按钮为9,
        # 所以用单击按钮的对象名称+1作为数据库中的id
        attention_info = mysql.query_id_info(cur, int(sender.objectName()) + 1)
        # 将商品名称显示在关注窗体的编辑框内
        attention.lineEdit.setText(attention_info[0])
        attention.open()  # 显示关注窗体
    
  4. 显示关注商品名称列表

    • 创建show_attention_name()方法来显示已关注商品的名称列表:
    def show_attention_name(self):
        self.name_list = []
        row, column, results = mysql.query_evaluate_info(cur, 'attention')
        if row != 0:
            for index, i in enumerate(results):
                self.name_list.append('关注商品' + str(index + 1) + ':\n' + i[1])
            font = QtGui.QFont()
            font.setPointSize(12)
            self.listView.setFont(font)
            self.listView.setEditTriggers(QtWidgets.QAbstractItemView.NoEditTriggers)
            self.listView.setWordWrap(True)
            model = QtCore.QStringListModel()
            model.setStringList(self.name_list)
            self.listView.setModel(model)
        else:
            model = QtCore.QStringListModel()
            model.setStringList(self.name_list)
            self.listView.setModel(model)
    
  5. 初始化关注窗体

    • 创建Attention类,并通过__init__()方法初始化关注窗体:
    class Attention(QMainWindow, Attention_MainWindow):
        def __init__(self):
            super(Attention, self).__init__()
            self.setupUi(self)
            # 开启自动填充背景
            self.centralwidget.setAutoFillBackground(True)
            palette = QtGui.QPalette()  # 调色板类
            palette.setBrush(QtGui.QPalette.Background, QtGui.QBrush(
                QtGui.QPixmap('img_resources/attention_bg.png')))  # 设置背景图片
            self.centralwidget.setPalette(palette)  # 为控件设置对应的调色板即可
            # 设置背景透明
            self.pushButton_yes.setStyleSheet("background-color:rgba(0,0,0,0)")
            # 设置确认关注按钮的背景图片
            self.pushButton_yes.setIcon(QtGui.QIcon('img_resources/yes_btn.png'))
            # 设置按钮背景图大小
            self.pushButton_yes.setIconSize(QtCore.QSize(100, 50))
            # 设置背景透明
            self.pushButton_no.setStyleSheet("background-color:rgba(0,0,0,0)")
            # 设置确认关注按钮的背景图片
            self.pushButton_no.setIcon(QtGui.QIcon('img_resources/no_btn.png'))
            # 设置按钮背景图大小
            self.pushButton_no.setIconSize(QtCore.QSize(100, 50))
    
  6. 插入关注商品信息到数据库

    • 创建insert_attention_message()方法,将商品信息插入数据库:
        # 打开关注窗体
        def open(self):
            self.show()
    
        def insert_attention_message(self, attention_info):
            is_identical = mysql.query_is_name(cur, attention_info[0])  # 判断数据库中是否已经关注了该商品
            if is_identical == 0:
                middle_time = mycrawl.get_evaluation(2, attention_info[2])
                poor_time = mycrawl.get_evaluation(1, attention_info[2])
                # 判断信息状态
                if middle_time != None and poor_time != None:
                    attention_info = attention_info + (middle_time, poor_time)  # 将评价时间添加至商品数据中
                    mysql.insert_attention(cur, [attention_info], 'attention')  # 插入关注信息
                    messageDialog('提示!', '已关注' + attention_info[0])  # 提示
                    attention.close()  # 关闭关注对话框
                    main.show_attention_name() # 显示关注商品的名称
                else:
                    print('无法获取评价时间!')
            else:
                messageDialog('警告!', '不可以关注相同的商品!')
                attention.close()
    
  7. 设置按钮事件

    • 在主程序的主入口处,创建关注窗体对象并设置按钮事件:
    attention = Attention()
    attention.pushButton_yes.clicked.connect(lambda: attention.insert_attention_message(attention_info))
    attention.pushButton_no.clicked.connect(attention.close)
    main.show_attention_name()
    
  8. 注册关注按钮信号槽

    • show_top10()方法中,注册关注按钮的信号槽:
    self.pushButton.clicked.connect(self.attention_btn)
    
  9. 运行并测试

    • 运行show_window.py文件,单击商品的“关注”按钮后,将弹出确认关注窗体,确认后会显示提示框并更新关注商品列表。

在这里插入图片描述
在这里插入图片描述

🦋2.2 取消关注

取消关注的小窗体与确认关注的小窗体相似,唯一不同的是背景图片和文字。以下是实现步骤:

class Cancel_Attention(QMainWindow, Attention_MainWindow):
    def __init__(self):
        super(Cancel_Attention, self).__init__()
        self.setupUi(self)
        # 开启自动填充背景
        self.centralwidget.setAutoFillBackground(True)
        palette = QtGui.QPalette()  # 调色板类
        palette.setBrush(QtGui.QPalette.Background, QtGui.QBrush(
            QtGui.QPixmap('img_resources/cancel_attention_bg.png')))  # 设置背景图片
        self.centralwidget.setPalette(palette)  # 为控件设置对应的调色板即可
        # 设置背景透明
        self.pushButton_yes.setStyleSheet("background-color:rgba(0,0,0,0)")
        # 设置确认关注按钮的背景图片
        self.pushButton_yes.setIcon(QtGui.QIcon('img_resources/yes_btn.png'))
        # 设置按钮背景图大小
        self.pushButton_yes.setIconSize(QtCore.QSize(100, 50))
        # 设置背景透明
        self.pushButton_no.setStyleSheet("background-color:rgba(0,0,0,0)")
        # 设置确认关注按钮的背景图片
        self.pushButton_no.setIcon(QtGui.QIcon('img_resources/no_btn.png'))
        # 设置按钮背景图大小
        self.pushButton_no.setIconSize(QtCore.QSize(100, 50))

    # 显示取消关注的窗体
    def open(self,qModeIndex):
        # 在关注商品名称列表中,获取单击了哪一个商品的名称
        name = main.name_list[qModeIndex.row()].lstrip('关注商品'+str(qModeIndex.row()+1)+':\n')
        # 将商品名称显示在关注窗体的编辑框内
        cancel_attention.lineEdit.setText(name)
        cancel_attention.show()  # 显示关注窗体

    #  取消关注的方法
    def unfollow(self):
        # 获取编辑框内的商品名称
        name = cancel_attention.lineEdit.text()
        mysql.delete_attention(cur,name)
        main.show_attention_name()     # 显示关注商品名称列表
        cancel_attention.close()       # 关掉取消关注的窗体

程序启动文件如下:

cancel_attention = Cancel_Attention()
# 指定显示关注商品名称列表事件
main.listView.clicked.connect(cancel_attention.open)
# 指定取消关注窗体按钮(是)单击事件处理方法
cancel_attention.pushButton_yes.clicked.connect(cancel_attention.unfollow)
# 指定取消关注窗体按钮(否)单击事件处理方法
cancel_attention.pushButton_no.clicked.connect(cancel_attention.close)

这样,整个关注与取消关注功能就完成了。
在这里插入图片描述
在这里插入图片描述

🔎3.显示商品分类比例饼图

在实现显示商品分类比例饼图时,首先需要创建一个图表文件,接着在该文件中创建用于显示饼图的方法。然后,将计算出的商品分类比例作为参数传递给该方法,最终将饼图显示在主窗体中。具体步骤如下:

🦋3.1 创建 chart.py 文件

首先,在项目文件夹中创建 chart.py 文件,并导入图表相关的模块。接着,创建 PlotCanvas 类,并在该类中通过 __init__() 方法进行初始化工作。代码如下:

# 图形画布
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
import matplotlib  # 导入图表模块
import matplotlib.pyplot as plt  # 导入绘图模块

class PlotCanvas(FigureCanvas):
    def __init__(self, parent=None, width=0, height=0, dpi=100):
        # 避免中文乱码
        matplotlib.rcParams['font.sans-serif'] = ['SimHei']
        matplotlib.rcParams['axes.unicode_minus'] = False
        fig = plt.figure(figsize=(width, height), dpi=dpi)  # 创建图形
        FigureCanvas.__init__(self, fig)
        self.setParent(parent)  # 设置父类

🦋3.2 创建 pie_chart() 方法显示饼图

PlotCanvas 类中,创建 pie_chart() 方法,用于显示商品分类的饼图。代码如下:

# 显示商品分类饼图
def pie_chart(self, size):
    # 绘制饼图
    explode = (0.1, 0, 0, 0, 0)  # 设置各部分突出
    label_list = ['鼠标', '键盘', 'U盘', '移动硬盘', '其他']  # 各部分标签
    plt.pie(size, labels=label_list, labeldistance=1.1, autopct="%1.1f%%", shadow=False, startangle=30, pctdistance=0.6)
    plt.axis("equal")  # 设置横轴和纵轴大小相等,这样饼才是圆的

🦋3.3 在 show_window.py 中导入自定义饼图类

show_window.py 文件中导入 PlotCanvas 类,并在 Main 类中创建 show_classification() 方法。该方法的功能是获取商品排名和数量,并统计商品分类比例。代码如下:

# 导入自定义饼图类
from chart import PlotCanvas

# 显示商品分类比例饼图
def show_classification(self):
    name_all = mysql.query_rankings_name(cur, 'jd_ranking')  # 获取排行榜中所有商品名称
    name_number = len(name_all)  # 获取商品总数量
    number = 0  # 定义统计分类数量的变量
    remove_list = []  # 保存需要移除的商品名称
    class_list = []  # 保存所有分类比例数据的列表

🦋3.4 排除重复商品名称并计算分类比例

为避免统计重复的商品名称(如“鼠标垫”和“鼠标”相似),首先移除这些商品,然后计算不同分类的占比。代码如下:

# 因为鼠标垫与鼠标名称接近,所以先移除鼠标垫
for name in name_all:
    if '鼠标垫' in name:
        remove_list.append(name)

# 循环移除鼠标垫相关商品
for r_name in remove_list:
    name_all.remove(r_name)

# 获取鼠标分类占有比例
for name in name_all:
    if '鼠标' in name:
        number += 1
mouse_ratio = float('%.1f' % ((number / name_number) * 100))  # 计算鼠标百分比
class_list.append(mouse_ratio)  # 向分类比例列表添加鼠标百分比数据

🦋3.5 计算其他商品分类的占比

依次计算键盘、U盘、移动硬盘和其他类别的占比。代码如下:

# 获取键盘占有比例
number = 0
for name in name_all:
    if '键盘' in name:
        number += 1
keyboard_ratio = float("%.1f" % ((number / name_number) * 100))
class_list.append(keyboard_ratio)

# 获取U盘占有比例
number = 0
for name in name_all:
    if 'U盘' in name or 'u盘' in name:
        number += 1
u_ratio = float('%.1f' % ((number / name_number) * 100))
class_list.append(u_ratio)

# 获取移动硬盘占有比例
number = 0
for name in name_all:
    if '移动硬盘' in name:
        number += 1
move_ratio = float('%.1f' % ((number / name_number) * 100))
class_list.append(move_ratio)

# 计算其他百分比
other_ratio = float('%.1f' % (100 - (mouse_ratio + keyboard_ratio + u_ratio + move_ratio)))
class_list.append(other_ratio)

🦋3.6 创建饼图并显示

创建 PlotCanvas 类对象,并调用 pie_chart() 方法将饼图添加到主窗体的布局中。代码如下:

# 创建饼图类对象
pie = PlotCanvas()

# 调用显示饼图的方法
pie.pie_chart(class_list)

# 将饼图添加到主窗体的水平布局中
self.horizontalLayout.addWidget(pie)

🦋3.7 调用 show_classification() 方法显示饼图

在主程序入口中,调用 show_classification() 方法来显示商品分类比例饼图。代码如下:

# 显示商品分类比例饼图
main.show_classification()

🦋3.8 运行并显示饼图

运行 show_window.py 文件时,主窗体的左上角将显示商品分类比例的饼图。

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2341266.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

HttpSessionListener 的用法笔记250417

HttpSessionListener 的用法笔记250417 以下是关于 HttpSessionListener 的用法详解,涵盖核心方法、实现步骤、典型应用场景及注意事项,帮助您全面掌握会话(Session)生命周期的监听与管理: 1. 核心功能 HttpSessionLi…

火山RTC 5 转推CDN 布局合成规则

实时音视频房间&#xff0c;转推CDN&#xff0c;文档&#xff1a; 转推直播--实时音视频-火山引擎 一、转推CDN 0、前提 * 在调用该接口前&#xff0c;你需要在[控制台](https://console.volcengine.com/rtc/workplaceRTC)开启转推直播功能。<br> * 调…

Spark两种运行模式与部署

1. Spark 的运行模式 部署Spark集群就两种方式&#xff0c;单机模式与集群模式 单机模式就是为了方便开发者调试框架的运行环境。但是生产环境中&#xff0c;一般都是集群部署。 现在Spark目前支持的部署模式&#xff1a; &#xff08;1&#xff09;Local模式&#xff1a;在本地…

qt画一朵花

希望大家的生活都更加美好&#xff0c;画一朵花送给大家 效果图 void FloatingArrowPubshButton::paintEvent(QPaintEvent *event) {QPainter painter(this);painter.setRenderHints(QPainter::Antialiasing);QPen pen;pen.setColor("green");pen.setWidth(5);QBrush…

服务器上安装maven

1.安装 下载安装包 https://maven.apache.org/download.cgi 解压安装包 cd /opt/software tar -xzvf apache-maven-3.9.9-bin.tar.gz 安装目录(/opt/maven/) mv /opt/software/apache-maven-3.9.9 /opt/ 3.权限设置 把/opt/software/apache-maven-3.9.9 文件夹重命名为ma…

UOS+N 卡 + CUDA 环境下 X86 架构 DeepSeek 基于 vLLM 部署与 Dify 平台搭建指南

一、文档说明 本文档是一份关于 DeepSeek 在X86架构下通vLLM工具部署的操作指南&#xff0c;主要面向需要在UOSN卡CUDA环境中部署DeepSeek的技术人员&#xff0c;旨在指导文档使用者完成从 Python 环境升级、vLLM 库安装、模型部署到 Dify 平台搭建的全流程操作。 二、安装Pyt…

MySQL终章(8)JDBC

目录 1.前言 2.正文 2.1JDBC概念 2.2三种编码方式 2.2.1第一种 2.2.2第二种&#xff08;优化版&#xff09; 2.2.3第三种&#xff08;更优化版&#xff09; 3.小结 1.前言 哈喽大家好吖&#xff0c;今天来给大家带来Java中的JDBC的讲解&#xff0c;之前学习的都是操作…

Python 爬虫如何伪装 Referer?从随机生成到动态匹配

一、Referer 的作用与重要性 Referer 是 HTTP 请求头中的一个字段&#xff0c;用于标识请求的来源页面。它在网站的正常运行中扮演着重要角色&#xff0c;例如用于统计流量来源、防止恶意链接等。然而&#xff0c;对于爬虫来说&#xff0c;Referer 也可能成为被识别为爬虫的关…

【MySQL】表的约束(主键、唯一键、外键等约束类型详解)、表的设计

目录 1.数据库约束 1.1 约束类型 1.2 null约束 — not null 1.3 unique — 唯一约束 1.4 default — 设置默认值 1.5 primary key — 主键约束 自增主键 自增主键的局限性&#xff1a;经典面试问题&#xff08;进阶问题&#xff09; 1.6 foreign key — 外键约束 1.7…

基于STC89C52RC和8X8点阵屏、独立按键的小游戏《打砖块》

目录 系列文章目录前言一、效果展示二、原理分析三、各模块代码1、8X8点阵屏2、独立按键3、定时器04、定时器1 四、主函数总结 系列文章目录 前言 用的是普中A2开发板&#xff0c;外设有&#xff1a;8X8LED点阵屏、独立按键。 【单片机】STC89C52RC 【频率】12T11.0592MHz 效…

数字电子技术基础(五十)——硬件描述语言简介

目录 1 硬件描述语言简介 1.1 硬件描述语言简介 1.2 硬件编程语言的发展历史 1.3 两种硬件描述的比较 1.4 硬件描述语言的应用场景 1.5 基本程序结构 1.5.1 基本程序结构 1.5.2 基本语句和描述方法 1.5.3 仿真 1 硬件描述语言简介 1.1 硬件描述语言简介 硬件描述语…

【深度学习】【目标检测】【Ultralytics-YOLO系列】YOLOV3核心文件common.py解读

【深度学习】【目标检测】【Ultralytics-YOLO系列】YOLOV3核心文件common.py解读 文章目录 【深度学习】【目标检测】【Ultralytics-YOLO系列】YOLOV3核心文件common.py解读前言autopad函数Conv类__init__成员函数forward成员函数forward_fuse成员函数 Bottleneck类__init__成员…

16.Chromium指纹浏览器开发教程之WebGPU指纹定制

WebGPU指纹概述 WebGPU是下一代的Web图形和计算API&#xff0c;旨在提供高性能的图形渲染和计算能力。它是WebGL的后继者&#xff0c;旨在利用现代GPU的强大功能&#xff0c;使得Web应用能够实现接近原生应用的图形和计算性能。而且它是一个低级别的API&#xff0c;可以直接与…

SQL预编译——预编译真的能完美防御SQL注入吗

SQL注入原理 sql注入是指攻击者拼接恶意SQL语句到接受外部参数的动态SQL查询中&#xff0c;程序本身 未对插入的SQL语句进行过滤&#xff0c;导致SQL语句直接被服务端执行。 拼接的SQL查询例如&#xff0c;通过在id变量后插入or 11这样的条件&#xff0c;来绕过身份验证&#…

运行neo4j.bat console 报错无法识别为脚本,PowerShell 教程:查看语言模式并通过注册表修改受限模式

无法将“D:\neo4j-community-4.4.38-windows\bin\Neo4j-Management\Get-Args.ps1”项识别为cmdlet、函数、脚本文件或可运行程序的名称。请检查名称的拼写&#xff0c;如果包括路径&#xff0c;请确保路径正确&#xff0c;然后再试一次。 前提配置好环境变量之后依然报上面的错…

【EDA软件】【设计约束和分析操作方法】

1. 设计约束 设计约束主要分为物理约束和时序约束。 物理约束主要包括I/O接口约束&#xff08;如引脚分配、电平标准设定等物理属性的约束&#xff09;、布局约束、布线约束以及配置约束。 时序约束是FPGA内部的各种逻辑或走线的延时&#xff0c;反应系统的频率和速度的约束…

【Lua】Lua 入门知识点总结

Lua 入门学习笔记 本教程旨在帮助有编程基础的学习者快速入门Lua编程语言。包括Lua中变量的声明与使用&#xff0c;包括全局变量和局部变量的区别&#xff0c;以及nil类型的概念、数值型、字符串和函数的基本操作&#xff0c;包括16进制表示、科学计数法、字符串连接、函数声明…

光谱相机在肤质检测中的应用

光谱相机在肤质检测中具有独特优势&#xff0c;能够通过多波段光谱分析皮肤深层成分及生理状态&#xff0c;实现‌非侵入式、高精度、多维度的皮肤健康评估‌。以下是其核心应用与技术细节&#xff1a; ‌一、工作原理‌ ‌光谱反射与吸收特性‌&#xff1a; ‌血红蛋白‌&a…

机器学习第一篇 线性回归

数据集&#xff1a;公开的World Happiness Report | Kaggle中的happiness dataset2017. 目标&#xff1a;基于GDP值预测幸福指数。&#xff08;单特征预测&#xff09; 代码&#xff1a; 文件一&#xff1a;prepare_for_traning.py """用于科学计算的一个库…

CS144 Lab1实战记录:实现TCP重组器

文章目录 1 实验背景与要求1.1 TCP的数据分片与重组问题1.2 实验具体任务 2 重组器的设计架构2.1 整体架构2.2 数据结构设计 3 重组器处理的关键场景分析3.1 按序到达的子串&#xff08;直接写入&#xff09;3.2 乱序到达的子串&#xff08;需要存储&#xff09;3.3 与已处理区…