You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

tkinter dynamic Checkbutton获取返回值实现问答跳转问题求助

问题修正方案

原代码核心问题

  • 变量作用域错误:当前题目对应的正确分组key、问题Q均为全局变量,循环后只保留最后一次赋值的结果,出题时无法拿到当前题目的正确校验依据
  • Checkbutton变量定义错误:chkValue初始为单个IntVar实例,无法按下标存储多个选项的选中状态
  • 界面组件未做重置:每次出题没有清空上一轮的组件,会导致界面元素堆叠无法使用
  • 事件绑定逻辑不合理:给每个Checkbutton绑定跳转事件,用户刚选第一个选项就会触发下一题,不符合答题交互逻辑

实现思路调整

  • 采用Tkinter原生的事件驱动模式,不需要主动暂停程序,新增提交按钮,用户完成选择后主动点击触发校验即可
  • 每次出题前清空上一轮的所有问题、选项、按钮组件
  • 用列表存储每个选项对应的选中状态变量,提交时遍历校验选中值是否属于当前分组
  • 把当前题目对应的正确分组、选项列表存在全局变量,供校验函数调用

可运行修正代码

import tkinter as tk
from tkinter import messagebox
import random

# 初始化窗口
window = tk.Tk()
window.geometry("400x300")

# 全局变量存储当前题目相关信息
current_correct_group = None
current_question = None
option_vars = []
option_widgets = []
submit_btn = None
question_label = None

def load_data():
    # 读取文件构造分组字典
    cpll = {}
    idx = 0
    with open('cpll.txt', 'r', encoding='utf-8') as f:
        lines = f.readlines()
    for line in lines:
        if line == "\n":
            idx += 1
        else:
            cpll.setdefault(idx, []).append(line.strip())
    return cpll

def clear_old_widgets():
    # 清空上一轮的所有组件
    global question_label, submit_btn
    if question_label:
        question_label.destroy()
    for widget in option_widgets:
        widget.destroy()
    if submit_btn:
        submit_btn.destroy()
    option_vars.clear()
    option_widgets.clear()

def quiz():
    global current_correct_group, current_question, question_label, submit_btn
    clear_old_widgets()
    # 随机选一个分组作为当前正确分组
    current_correct_group = random.choice(list(cpll.values()))
    # 抽一个当问题
    current_question = random.choice(current_correct_group)
    # 生成备选答案:当前分组剩余元素 + 其他分组随机选2个干扰项,不需要干扰项可删除对应逻辑
    options = [i for i in current_correct_group if i != current_question]
    other_groups = [v for k,v in cpll.items() if v != current_correct_group]
    for g in other_groups:
        options.extend(random.sample(g, 1))
    # 打乱选项
    random.shuffle(options)
    # 展示问题
    question_label = tk.Label(window, text=f"请选择与【{current_question}】同组的选项", bg="skyblue", width=40)
    question_label.pack(pady=10)
    # 生成选项Checkbutton
    for opt in options:
        var = tk.IntVar()
        chk = tk.Checkbutton(window, text=opt, variable=var)
        chk.pack(anchor='w', padx=50)
        option_vars.append((opt, var))
        option_widgets.append(chk)
    # 提交按钮
    submit_btn = tk.Button(window, text="提交答案", command=check_answer)
    submit_btn.pack(pady=15)

def check_answer():
    # 校验选中的选项是否都属于当前正确分组
    selected = [opt for opt, var in option_vars if var.get() == 1]
    all_correct = all([i in current_correct_group for i in selected])
    if all_correct and len(selected) > 0:
        # 答对进入下一轮
        quiz()
    else:
        # 答错提示
        messagebox.showwarning("错误", "选择有误,请重新选择")

# 加载数据
cpll = load_data()
# 开始第一轮出题
quiz()
window.mainloop()

内容的提问来源于stack exchange,提问作者user1582596

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 13:27:02