Python选择题训练工具:高效学习、答题回顾与音频朗读一站式体验
一、引言
随着人工智能技术的不断进步,传统的教学方式已经逐渐向智能化、互动化转变。在众多英语测试题型中,选择题作为一种高效的方式被广泛应用于各类培训与考试中。为了帮助学生高效学习与自测,本篇文章将采用Python编写一款基于 Python 开发的选择题训练工具。该工具不仅支持加载 Excel 文件中的题库,还具备题干和选项展示、答题记录、音频朗读等多种功能,旨在为用户提供便捷、高效的学习体验。
二、开发背景
在日常教学过程中,老师往往需要准备大量的选择题作为测试题目。我们可以把这些题目存储在 Excel 文件中,如果手动处理和展示题目会非常繁琐。为了提高教学效率,选用一种自动化展示工具成为一种迫切的需求。本项目通过 Python 和 Tkinter 库实现了一个图形化界面应用,可以自动加载并展示选择题,记录用户答题情况,同时通过音频朗读题目,进一步增强互动性。软件的示意图如下:
软件展示
三、软件特点
- 题库加载与展示:支持从 Excel 文件中加载选择题,并且可以根据课程单元名称筛选题目。
- 音频朗读功能:使用 Python 的 Pygame 库播放题目音频,即朗读题干,帮助用户通过听力巩固已学单词。
- 答题记录与统计:软件会自动记录用户的答题情况,并在决定答题结束时,提供正确率和错误题目的回顾功能。
- 多线程支持:使用线程处理音频播放等耗时操作,避免界面卡顿,提升用户体验。同时,当完成一道题时,会自动转到下一道,并给出正确或错误的提示。正确就是显示绿色button选项,错误就显示红色button选项。
- 图形化界面:基于 Tkinter 实现的 GUI 界面,简单直观,易于操作。
四、使用方法
1. 安装依赖
在运行程序之前,需要安装一些 Python 库,依赖包括 openpyxl, pygame 和 requests。可以使用以下命令安装所需的库:
pip install openpyxl pygame requests
2. 准备题库
本程序需要一个 Excel 文件,并命名为【选择题.xlsx】作为题库,Excel 文件应包括如下列:
- 单元:课程名称或章节
- 序号:题目的编号
- 题干:选择题的内容
- 选项A、B、C、D:四个选择项
- 正确答案:正确的答案选项
Excel表的内容如下:
Excel表内容
3. 运行程序
运行 Python 程序,tkinter GUI界面会自动加载,用户可以在顶部下拉框选择不同的课程,然后开始答题,结束前查看战绩,回顾错误题目,还可以点朗读通过音频功能听题干。
4. 功能概览
- 选择题显示:在每道题目显示时,用户可以选择答案。程序会自动判断正确与否,并高亮显示选择的答案。
- 战绩统计:用户答题完成后,可以查看自己的正确率统计。
- 错误回顾:用户可以查看答错的题目,并且看到正确答案与自己的选择。
- 朗读功能:用户可以点击按钮让程序朗读题干。
五、源码展示
以下是该程序的主要代码:
import tkinter as tk
from tkinter import ttk, messagebox
from openpyxl import load_workbook
import random
import os,re
import pygame,requests
from io import BytesIO
from threading import Lock, Thread, Timerdef load_excel_data(filename):workbook = load_workbook(filename)sheet = workbook.activequestions = []lessons = set() # 用于存储所有课程名,避免重复for row in sheet.iter_rows(min_row=2, values_only=True):lesson = row[0]lessons.add(lesson)question = {'单元': lesson,'序号': row[1],'题干': row[2],'选项': [row[3], row[4], row[5], row[6]],'正确答案': row[7]}questions.append(question)return list(lessons), questionslessons, questions = load_excel_data('选择题.xlsx')
random.shuffle(questions)# 使用正则表达式从课程名中提取数字,并按数字排序课程名
sorted_lessons = sorted(lessons, key=lambda x: (lambda m: int(m.group(0)) if m else 0)(re.search(r'\d+', x)))class QuizApp:def __init__(self, root):self.root = root# 设置窗口大小self.root.geometry("600x500")#self.root.resizable(False, False)pygame.init()self.all_questions = questionsself.questions = questions # 当前显示的问题列表self.current_question_index = 0self.correct_answers = 0self.wrong_answers = 0self.error_questions = []self.setup_ui()self.load_question()def thread_it(self,func):self.thread1=Thread(target=func)self.thread1.setDaemon(True) self.thread1.start()def setup_ui(self):self.root.title("选择题训练工具")self.lesson_combobox = ttk.Combobox(self.root, values=['全部'] + sorted_lessons, state="readonly")self.lesson_combobox.pack(pady=(10, 0))self.lesson_combobox.set('全部')self.lesson_combobox.bind('<<ComboboxSelected>>', self.on_combobox_change)self.question_label = tk.Label(self.root, text="", font=("Times New Roman", 20), fg="blue", wraplength=520, justify=tk.LEFT) #设置文本长度,并且文本左对齐self.question_label.pack(pady=(10, 40))self.options_frame = tk.Frame(self.root)self.options_frame.pack(pady=20)option_labels = ['A', 'B', 'C', 'D'] # 选项标签self.option_buttons = [] # 存储选项按钮self.option_labels = [] # 存储选项标签控件for i in range(4):# 创建选项标签控件并放置label = tk.Label(self.options_frame, text=f"{option_labels[i]}.", font=("Times New Roman", 16))label.grid(row=i, column=0, pady=5, sticky="e")self.option_labels.append(label)# 创建选项按钮并放置btn = tk.Button(self.options_frame, text="", font=("Times New Roman", 16), width=20,command=lambda b=i: self.check_answer(b), # type: ignoreanchor="w")btn.grid(row=i, column=1, pady=5)self.option_buttons.append(btn)self.action_frame = tk.Frame(self.root)self.action_frame.pack(side=tk.BOTTOM, pady=20)tk.Button(self.action_frame, text="退出程序", font=("宋体", 16, "bold"), width=9, command=self.ui_quit).pack(side=tk.LEFT, padx=10)tk.Button(self.action_frame, text="我的战绩", font=("宋体", 16, "bold"), width=9, command=self.show_score).pack(side=tk.LEFT, padx=10)tk.Button(self.action_frame, text="查看错误", font=("宋体", 16, "bold"), width=9, command=self.show_errors).pack(side=tk.LEFT, padx=10)tk.Button(self.action_frame, text="朗读题干", font=("宋体", 16, "bold"), width=9, command=self.show_sound).pack(side=tk.LEFT, padx=10)# 其余UI代码与原来相同...def on_combobox_change(self, event):selected_lesson = self.lesson_combobox.get()if selected_lesson == '全部':self.questions = self.all_questionselse:self.questions = [q for q in self.all_questions if q['单元'] == selected_lesson]self.current_question_index = 0self.correct_answers = 0self.wrong_answers = 0self.error_questions = []self.load_question()def load_question(self):if self.current_question_index < len(self.questions):question = self.questions[self.current_question_index]self.question_label.config(text=str(self.current_question_index+1)+". "+question['题干'],anchor='w')correct_answer = question['正确答案']options = question['选项']self.correct_option_index = options.index(correct_answer)random.shuffle(options)for i, option in enumerate(options):self.option_buttons[i].config(text=option, bg='SystemButtonFace')def check_answer(self, button_index):question = self.questions[self.current_question_index]selected_option = self.option_buttons[button_index].cget('text')correct_option = question['正确答案']# 确定正确答案按钮的索引correct_option_index = Nonefor i, btn in enumerate(self.option_buttons):if btn.cget('text') == correct_option:correct_option_index = ibreakif selected_option == correct_option:# 用户选择了正确的答案self.option_buttons[button_index].config(bg='light green')self.correct_answers += 1else:# 用户选择了错误的答案self.option_buttons[button_index].config(bg='red')if correct_option_index is not None:self.option_buttons[correct_option_index].config(bg='light green')self.wrong_answers += 1self.error_questions.append((question['题干'], selected_option, question['正确答案']))# 准备间隔1秒显示下一个问题self.root.after(1000, self.next_question)def next_question(self):self.current_question_index += 1if self.current_question_index < len(self.questions):self.load_question()else:messagebox.showinfo("结束", "所有问题都已回答完毕!")def ui_quit(self):self.root.destroy()def show_score(self):messagebox.showinfo("战绩", f"正确: {self.correct_answers}\n错误: {self.wrong_answers}\n总计: {len(self.questions)}\n正确率:{self.correct_answers/len(self.questions)*100}%")def show_sound(self):self.thread_it(self.show_sound2)def show_errors(self):error_messages = "\n".join([f"题干: {q[0]},正确答案是:{q[2]}, 您的选择: {q[1]}" for q in self.error_questions])messagebox.showinfo("错误回顾", error_messages if error_messages else "完美!没有任何错误。")def show_sound2(self):self.current_name = self.question_label.cget("text")audio_path = f"https://dict.youdao.com/dictvoice?audio={self.current_name}&type=1"resp = requests.get(audio_path)audio_data = BytesIO(resp.content)pygame.mixer.music.load(audio_data)pygame.mixer.music.play()while pygame.mixer.music.get_busy():continue# 退出pygameif __name__ == "__main__":root = tk.Tk()app = QuizApp(root)root.mainloop()
六、注意事项
- Excel 文件格式:确保题库文件【
选择题.xlsx】
的格式正确,每个问题必须包含单元、序号、题干、选项和正确答案等字段。 - 音频播放:程序中使用了 Pygame 库进行音频播放,因此需要安装相应的音频库,并且程序会访问在线字典接口生成题目音频。
- 线程管理:为了避免界面卡顿,音频播放等操作被放置在单独的线程中处理,保证主界面的流畅性。
- 数据存储:答题结果和错误回顾会暂时保存在程序内存中,但如果需要长期保存数据,可以考虑添加导出功能。
七、总结
这款选择题训练工具通过 Python 实现了一个简单易用的答题系统,利用 Tkinter 提供了良好的用户界面,结合 Pygame 和音频播放技术,增强了选择题问答的互动性。它可以帮助学生提高学习效率,帮助教师管理题库,并提供了直观的成绩统计与错误回顾功能,是一款非常实用的教学辅助工具。
相关文章:

Python选择题训练工具:高效学习、答题回顾与音频朗读一站式体验
一、引言 随着人工智能技术的不断进步,传统的教学方式已经逐渐向智能化、互动化转变。在众多英语测试题型中,选择题作为一种高效的方式被广泛应用于各类培训与考试中。为了帮助学生高效学习与自测,本篇文章将采用Python编写一款基于 Python …...
Python实现机器学习驱动的智能医疗预测模型系统的示例代码框架
以下是一个使用Python实现机器学习驱动的智能医疗预测模型系统的示例代码框架。这个框架涵盖了数据收集(爬虫)、数据清洗和预处理、模型构建(决策树和神经网络)以及模型评估的主要步骤。 1. 数据收集(爬虫)…...

AWS Certified AI Practitioner 自学考试心得
学习目标: 考取 AWS Certified AI Practitioner 那什么是 AWS Certified AI Practitioner 认证 是基础级的认证 比较简单 — 学习内容: 1. AWS网站自学网站 极客时间免费课程:http://gk.link/a/12sJL 配合极客时间课程的章节测试检验自…...
JQ中的each()方法与$.each()函数的使用区别
介绍 jquery里的 each() 是一个强大的遍历工具,用于迭代集合中的元素,并为每个元素执行指定的函数。它既可以用于遍历 jQuery对象集合,也可以用于遍历普通的数组或对象。 each()对象遍历 语法: $(selector).each(function(in…...

滚珠丝杆与直线导轨的区别
滚珠丝杆和直线导轨是两种常见的精密机械传动装置,它们的作用是实现直线运动,在工业自动化和精密机械领域中扮演着重要的角色。尽管它们都用于实现直线运动,但它们在结构以及性能特点上还是存在一些区别: 一、工作原理 1、滚珠丝…...

【Ovis】Ovis1.6的本地部署及推理
Ovis简介 Ovis是阿里国际AI团队开源的多模态大模型,看新闻介绍效果不错,在多个场景的测试下都能达到SOTA,其中的Ovis1.6-Gemma2-9B在30B参数以下的模型中取得了综合排名第一,赶超MiniCPM-V-2.6等行业优秀大模型。所以我也部署一个…...

C语言结构体位定义(位段)的实际作用深入分析
1、结构体位段格式 struct struct_name {type [member_name] : width; };一般定义结构体,成员都是int、char等类型,占用的空间大小是固定的在成员名称后用冒号来指定位宽,可以指定每个成员所占用空间,并且也不用受结构体成员起始…...
儿童影楼管理系统:基于SSM的创新设计与功能实现
3.1系统的需求分析 需求分析阶段是设计系统功能模块的总方向,可以这样来说,系统的整个的开发流程以及设计进度,基本上都是以需求分析为基本依据的[10]。需求分析阶段可以确定系统的基本功能设计,以及在最后的系统验收阶段…...

青蛇人工智能学家
青蛇人工智能学家 青蛇,是蓝星上,最出名的人工智能学家。 在蓝星上,大家都知道,青蛇人工智能学家,最大的爱好,是美食。 青蛇人工智能学家,对自己的食物,非常在意,对自己的…...
uniapp+vue 前端防多次点击表单,防误触多次请求方法。
最近项目需求写了个uniappvue前端H5,有个页面提交表单的时候发现会有用户乱点导致数据库多条重复脏数据。故需要优化,多次点击表单只请求一次。 思路: 直接调用uni.showToast,点完按钮跳一个提交成功的提示。然后把防触摸穿透mask设置成true就行&#…...
【ES6复习笔记】rest参数(7)
什么是 rest 参数? rest 参数是 ES6 引入的一个特性,它允许我们将一个不定数量的参数表示为一个数组。使用 rest 参数可以更方便地处理函数的参数,尤其是在参数数量不确定的情况下。 如何使用 rest 参数? 在函数定义中…...
Hive SQL 窗口函数 `ROW_NUMBER() ` 案例分析
一文彻底搞懂 ROW_NUMBER() 和 PARTITION BY 1. 引言 在处理大规模数据集时,Hive SQL 提供了强大的窗口函数(Window Function),如 ROW_NUMBER(),用于为结果集中的每一行分配唯一的行号。当与 PARTITION BY 和 ORDER …...

前端mock数据 —— 使用Apifox mock页面所需数据
前端mock数据 —— 使用Apifox 一、使用教程二、本地请求Apifox所mock的接口 一、使用教程 在首页进行新建项目: 新建项目名称: 新建接口: 创建json: 请求方法: GET。URL: api/basis。响应类型…...

车载U盘制作教程:轻松享受个性化音乐
车载U盘播放音乐相较于蓝牙播放具有一些明显的优势,这些优势主要体现在音质、稳定性、音乐管理以及兼容性等方面。以下是车载U盘播放音乐的一些优势: 音质更佳:车载U盘播放音乐时,音乐文件是直接被解码并播放的,这意味…...
springboot 3 websocket react 系统提示,选手实时数据更新监控
构建一个基于 Spring Boot 3 和 WebSocket 的实时数据监控系统,并在前端使用 React,可以实现选手实时数据的更新和展示功能。以下是该系统的核心设计和实现思路: 1. 系统架构 后端 (Spring Boot 3): 提供 WebSocket 服务端,处理…...

现代图形API综合比较:Vulkan DirectX Metal WebGPU
Vulkan、DirectX、Metal 和 WebGPU 等低级图形 API 正在融合为类似于当前 GPU 构建方式的模型。 图形处理单元 (GPU) 是异步计算单元,可以处理大量数据,例如复杂的网格几何形状、图像纹理、输出帧缓冲区、变换矩阵或你想要计算的任何数据。 NSDT工具推荐…...
【Hot100刷题计划】Day04 栈专题 1~3天回顾(持续更新)
LeetCode Hot 100 是最常被考察的题目集合,涵盖了面试中常见的算法和数据结构问题。刷 Hot100可以让你在有限的时间内集中精力解决最常考的问题。鼓励大家不仅要写出代码,最好理解问题的本质、优化解法和复杂度分析。遇到问题要多交流多求问多分享&#…...

用VBA将word文档处理成支持弹出式注释的epub文档可用的html内容
有一种epub文件,其中的注释以弹窗形式显示,如下图: 点击注释引用后,对应的注释内容会弹出在页面中显示,再次点击弹窗外的任意位置该弹窗即关闭,关闭后点击任意注释引用,对应的注释内容会弹窗显示…...

舵机原理介绍 简洁讲解面向实战 非阻塞式驱动代码, arduino
目录 1.舵机简介 2.舵机转动角度的PWM条件(以180度的SG90舵机为例) 2.1 控制关系 2.2arduino产生PWM 3.0 附代码 循环0度到180度开关舵机(非阻塞版本) 4.0 Servo.h 舵机代码 1.舵机简介 舵机也叫伺服电机,是控制输入PWM信号来精确控制转动角度.所以想要驱动舵机就是让ard…...
Oracle Database 23ai 中的DBMS_HCHECK
在 Oracle 23ai 中,DBMS_HCHECK 包允许我们检查数据库中已知的数据字典问题。 几年前,Oracle 发布了 hcheck.sql 脚本(文档 ID 136697.1)来检查数据库中已知的数据字典问题。 DBMS_HCHECK 包意味着我们不再需要下载 hcheck.sql…...

智能在线客服平台:数字化时代企业连接用户的 AI 中枢
随着互联网技术的飞速发展,消费者期望能够随时随地与企业进行交流。在线客服平台作为连接企业与客户的重要桥梁,不仅优化了客户体验,还提升了企业的服务效率和市场竞争力。本文将探讨在线客服平台的重要性、技术进展、实际应用,并…...
Java - Mysql数据类型对应
Mysql数据类型java数据类型备注整型INT/INTEGERint / java.lang.Integer–BIGINTlong/java.lang.Long–––浮点型FLOATfloat/java.lang.FloatDOUBLEdouble/java.lang.Double–DECIMAL/NUMERICjava.math.BigDecimal字符串型CHARjava.lang.String固定长度字符串VARCHARjava.lang…...

屋顶变身“发电站” ,中天合创屋面分布式光伏发电项目顺利并网!
5月28日,中天合创屋面分布式光伏发电项目顺利并网发电,该项目位于内蒙古自治区鄂尔多斯市乌审旗,项目利用中天合创聚乙烯、聚丙烯仓库屋面作为场地建设光伏电站,总装机容量为9.96MWp。 项目投运后,每年可节约标煤3670…...
python如何将word的doc另存为docx
将 DOCX 文件另存为 DOCX 格式(Python 实现) 在 Python 中,你可以使用 python-docx 库来操作 Word 文档。不过需要注意的是,.doc 是旧的 Word 格式,而 .docx 是新的基于 XML 的格式。python-docx 只能处理 .docx 格式…...
今日科技热点速览
🔥 今日科技热点速览 🎮 任天堂Switch 2 正式发售 任天堂新一代游戏主机 Switch 2 今日正式上线发售,主打更强图形性能与沉浸式体验,支持多模态交互,受到全球玩家热捧 。 🤖 人工智能持续突破 DeepSeek-R1&…...

有限自动机到正规文法转换器v1.0
1 项目简介 这是一个功能强大的有限自动机(Finite Automaton, FA)到正规文法(Regular Grammar)转换器,它配备了一个直观且完整的图形用户界面,使用户能够轻松地进行操作和观察。该程序基于编译原理中的经典…...

基于TurtleBot3在Gazebo地图实现机器人远程控制
1. TurtleBot3环境配置 # 下载TurtleBot3核心包 mkdir -p ~/catkin_ws/src cd ~/catkin_ws/src git clone -b noetic-devel https://github.com/ROBOTIS-GIT/turtlebot3.git git clone -b noetic https://github.com/ROBOTIS-GIT/turtlebot3_msgs.git git clone -b noetic-dev…...

RabbitMQ入门4.1.0版本(基于java、SpringBoot操作)
RabbitMQ 一、RabbitMQ概述 RabbitMQ RabbitMQ最初由LShift和CohesiveFT于2007年开发,后来由Pivotal Software Inc.(现为VMware子公司)接管。RabbitMQ 是一个开源的消息代理和队列服务器,用 Erlang 语言编写。广泛应用于各种分布…...
解决:Android studio 编译后报错\app\src\main\cpp\CMakeLists.txt‘ to exist
现象: android studio报错: [CXX1409] D:\GitLab\xxxxx\app.cxx\Debug\3f3w4y1i\arm64-v8a\android_gradle_build.json : expected buildFiles file ‘D:\GitLab\xxxxx\app\src\main\cpp\CMakeLists.txt’ to exist 解决: 不要动CMakeLists.…...

基于Java+VUE+MariaDB实现(Web)仿小米商城
仿小米商城 环境安装 nodejs maven JDK11 运行 mvn clean install -DskipTestscd adminmvn spring-boot:runcd ../webmvn spring-boot:runcd ../xiaomi-store-admin-vuenpm installnpm run servecd ../xiaomi-store-vuenpm installnpm run serve 注意:运行前…...