Python员工管理系统CSV导入及文件覆盖问题技术求助
员工管理系统问题修复方案
问题1:保存数据覆盖旧记录,重启后丢失历史数据
问题原因
- 保存函数使用
"w"模式打开CSV文件,会直接清空原有内容后写入新数据 - 程序启动时未将已有CSV数据加载到
main_lst,新增数据仅在内存暂存,重启后丢失
修复方案
- 启动时读取现有CSV数据(跳过表头)加载到
main_lst和Data列表 - 保存时将
main_lst中的所有数据(原有+新增)写入文件,确保数据完整
问题2:完善CSV/Excel数据导入GUI展示功能
问题原因
当前OpenFile仅打印文件内容,未将数据解析后更新GUI列表和数据存储
修复方案
- 修改
OpenFile函数,解析选中的CSV/Excel文件,合并到现有数据集合 - 自动刷新Listbox展示新导入的员工姓名,支持查看导入的员工详情
- 新增Excel解析支持(需额外安装依赖库)
完整修复后代码
import csv from tkinter import * from tkinter import filedialog import tkinter.messagebox # 全局变量定义 window=Tk() window.geometry("800x500+0+0") window.title("Employee Management System") window.maxsize(width=800,height=500) window.minsize(width=800,height=500) main_lst=[] Data=[] # 存储员工详情数据 listbox1 = None NameLabel2 = None AgeLabel2 = None GenderLabel2 = None PositionLabel2 = None AddressLabel2 = None # 程序启动时加载现有CSV数据 def load_initial_data(): global main_lst, Data file_path = '/Users/nhal-naffakh/Desktop/Desktop/Sec-Interview/Data.csv' try: with open(file_path, 'r') as file: reader = csv.reader(file) next(reader) # 跳过表头 Data = list(reader) main_lst = Data.copy() # 将已有数据加载到main_lst update_name_listbox() except FileNotFoundError: # 文件不存在时创建空文件并写入表头 with open(file_path, 'w') as file: writer = csv.writer(file) writer.writerow(["Fullname","Age","Gender","Position","Phone Number","Address"]) def update_name_listbox(): global listbox1 List_of_Name = [row[0] for row in Data] var = StringVar(value=List_of_Name) listbox1.config(listvariable=var) def view(): if not listbox1.curselection(): messagebox.showwarning("提示", "请选择要查看的员工") return index=listbox1.curselection()[0] NameLabel2.config(text=Data[index][0]) AgeLabel2.config(text=Data[index][1]) GenderLabel2.config(text=Data[index][2]) PositionLabel2.config(text=Data[index][3]) AddressLabel2.config(text=Data[index][5]) # 修复地址列索引错误 def OpenFile(): global Data, main_lst filepath=filedialog.askopenfilename(filetypes=[("CSV文件", "*.csv"), ("Excel文件", "*.xlsx *.xls")]) if not filepath: return try: if filepath.endswith('.csv'): with open(filepath,'r') as file: reader = csv.reader(file) next(reader) imported_data = list(reader) # 按姓名去重,避免重复导入 existing_names = {row[0] for row in Data} new_data = [row for row in imported_data if row[0] not in existing_names] Data.extend(new_data) main_lst.extend(new_data) update_name_listbox() messagebox.showinfo("成功", f"导入{len(new_data)}条新数据") elif filepath.endswith(('.xlsx', '.xls')): # 需先安装依赖:pip install pandas openpyxl import pandas as pd df = pd.read_excel(filepath) imported_data = df.values.tolist() existing_names = {row[0] for row in Data} new_data = [row for row in imported_data if row[0] not in existing_names] Data.extend(new_data) main_lst.extend(new_data) update_name_listbox() messagebox.showinfo("成功", f"导入{len(new_data)}条新数据") except Exception as e: messagebox.showerror("错误", f"导入失败:{str(e)}") def Add(): global main_lst, Data name = Nametxt.get().strip() age = Agetxt.get().strip() gender = Gendertxt.get().strip() position = Positiontxt.get().strip() number = Numbertxt.get().strip() address = Addresstxt.get().strip() if not all([name, age, gender, position, number, address]): messagebox.showwarning("提示", "请填写所有字段") return lst=[name, age, gender, position, number, address] main_lst.append(lst) Data.append(lst) update_name_listbox() messagebox.showinfo("成功","数据已添加") def Save(): file_path = '/Users/nhal-naffakh/Desktop/Desktop/Sec-Interview/Data.csv' with open(file_path,"w") as file: Writer=csv.writer(file) Writer.writerow(["Fullname","Age","Gender","Position","Phone Number","Address"]) Writer.writerows(main_lst) messagebox.showinfo("成功","保存完成") def Clear(): Nametxt.delete(0,END) Agetxt.delete(0,END) Gendertxt.delete(0,END) Positiontxt.delete(0,END) Numbertxt.delete(0,END) Addresstxt.delete(0,END) def Exit(): wayOut = tkinter.messagebox.askyesno("员工管理系统", "确定要退出吗?") if wayOut: window.destroy() # 创建GUI控件(移出循环,避免重复创建) def create_gui(): global listbox1, NameLabel2, AgeLabel2, GenderLabel2, PositionLabel2, AddressLabel2, Nametxt, Agetxt, Gendertxt, Positiontxt, Numbertxt, Addresstxt # 录入区域 Namelabel3=Label(window,text="Full Name",font=('arial',12,'bold'),bd=3,fg="white",bg="dark blue").grid(row=0,column=0,sticky="w") Nametxt=Entry(window,font=('ariel',12),bd=4,width=22, justify='left') Nametxt.grid(row=0,column=1) Agelabel3=Label(window,text="Age",font=("ariel",12,'bold'),bd=3,fg='white',bg="dark blue").grid(row=0,column=2) Agetxt=Entry(window,font=('ariel',12),bd=4, justify='left') Agetxt.grid(row=0,column=3) GenderLabel3=Label(window,text="Gender",font=('ariel',12,'bold'),bd=3,fg='white',bg="dark blue").grid(row=1,column=0,sticky="w") Gendertxt=Entry(window,font=('ariel',12),bd=4, justify='left') Gendertxt.grid(row=1,column=1) PositionLabel3=Label(window,text="Position",font=('ariel',12,'bold'),bd=3,fg='white',bg="dark blue").grid(row=1,column=2,sticky="w") Positiontxt=Entry(window,font=('ariel',12),bd=4, justify='left') Positiontxt.grid(row=1,column=3) NumberLabel3=Label(window,text="Mob Number",font=('ariel',12,'bold'),bd=3,fg='white',bg="dark blue").grid(row=2,column=0,sticky="w") Numbertxt=Entry(window,font=('ariel',12),bd=4, justify='left') Numbertxt.grid(row=2,column=1) AddressLabel3=Label(window,text="Address",font=('ariel',12,'bold'),bd=3,fg='white',bg="dark blue").grid(row=2,column=2,sticky="w") Addresstxt=Entry(window,font=('ariel',12),bd=4, justify='left') Addresstxt.grid(row=2,column=3) # 列表与按钮区域 listbox1=Listbox(window) listbox1.grid(row=3,column=0) Button(text="ViewRecord",padx=10, pady=4, bd=4, font=('ariel',12,'bold'),width=8,fg='black',bg="dark gray",command=view).grid(row=3,column=1) Button(text="Load File", padx=10, pady=4, bd=4, font=('ariel',12,'bold'),width=8,fg='black',bg="dark gray", command=OpenFile).grid(row=3,column=2) Button(text="Add Record", padx=10, pady=4, bd=4, font=('ariel',12,'bold'),width=8,fg='black',bg="dark gray",command=Add).grid(row=3,column=3) Button(text="Save", padx=10, pady=4, bd=4, font=('ariel',12,'bold'), width=8,fg='black',bg="dark gray",command=Save).grid(row=4,column=1) Button(text="Clear", padx=10, pady=4, bd=4, font=('ariel',12,'bold'), width=8,fg='black',bg="dark gray",command=Clear).grid(row=4,column=2) Button(text="Exit", padx=10, pady=4, bd=4, font=('ariel',12,'bold'),width=8,fg='black', bg="dark gray",command=Exit).grid(row=4,column=3) # 详情展示区域 Label(window,text="FullName").grid(row=5,column=0,sticky="w") Label(window,text="Age").grid(row=6,column=0,sticky="w") Label(window,text="Gender").grid(row=7,column=0,sticky="w") Label(window,text="Position").grid(row=8,column=0,sticky="w") Label(window,text="Address").grid(row=9,column=0,sticky="w") NameLabel2=Label(window,text="") NameLabel2.grid(row=5,column=1,sticky="w") AgeLabel2=Label(window,text="") AgeLabel2.grid(row=6,column=1,sticky="w") GenderLabel2=Label(window,text="") GenderLabel2.grid(row=7,column=1,sticky="w") PositionLabel2=Label(window,text="") PositionLabel2.grid(row=8,column=1,sticky="w") AddressLabel2=Label(window,text="") AddressLabel2.grid(row=9,column=1,sticky="w") # 初始化程序 create_gui() load_initial_data() window.mainloop()
关键修改说明
- 数据持久化修复:
- 新增
load_initial_data函数,启动时自动读取已有CSV数据 - 保存时写入所有数据,彻底解决覆盖问题
- 新增
- 导入功能完善:
- 支持CSV和Excel文件导入,自动合并去重
- 导入后实时刷新列表,可直接查看导入数据详情
- GUI优化:
- 将控件创建代码移出循环,避免重复生成多个相同控件
- 增加输入校验,防止空数据录入
- 修复查看详情时地址列的索引错误
内容的提问来源于stack exchange,提问作者Neamah
相关产品推荐
相关产品推荐

