#29 group_by Month

本文介绍如何使用group_by方法将任务列表按月份进行分组,并展示了一个实际的例子,即在一个Rails应用中,通过将任务按其截止日期的月份进行归类,从而实现了更加清晰的任务展示。
Learn how to use the very useful group_by method to group an array by anything you want! In this episode I group an array of tasks by month then sort it properly.
# tasks_controller.rb
def index
@tasks = Task.find(:all, :order => 'due_at, id', :limit => 50)
@task_months = @tasks.group_by { |t| t.due_at.beginning_of_month }
end
<!-- tasks/index.rhtml -->
<% @task_months.sort.each do |month, tasks| %>
<h2><%= month.strftime('%B') %></h2>
<% for task in tasks %>
<div class="task">
<strong><%= task.name %></strong>
due on <%= task.due_at.to_date.to_s(:long) %>
</div>
<% end %>
<% end %>
# # import tkinter as tk # from tkinter import ttk, filedialog, messagebox # from datetime import datetime # import os # # def filter_logs_by_time_and_keywords(log_file, start_time, end_time, keyword_dict): # matched_logs = [] # start_time = datetime.strptime(start_time, &#39;%Y-%m-%d %H:%M:%S&#39;) # end_time = datetime.strptime(end_time, &#39;%Y-%m-%d %H:%M:%S&#39;) # try: # with open(log_file, &#39;r&#39;, encoding=&#39;utf-8&#39;) as file: # for line in file: # try: # time_str = line.split(&#39;,&#39;)[0] # log_time = datetime.strptime(time_str, &#39;%Y-%m-%d %H:%M:%S&#39;) # if start_time <= log_time <= end_time: # for keyword in keyword_dict.keys(): # if keyword in line: # log_info = f"{time_str},{keyword_dict[keyword]},{line.strip()}" # matched_logs.append(log_info) # except ValueError: # continue # except FileNotFoundError: # messagebox.showerror("错误", "未找到指定的日志文件") # return matched_logs # # def select_log_file(): # file_path = filedialog.askopenfilename() # if file_path: # log_file_entry.delete(0, tk.END) # log_file_entry.insert(0, file_path) # # def run_filter(): # start_time = f"{start_year.get()}-{start_month.get()}-{start_day.get()} {start_hour.get()}:{start_minute.get()}:{start_second.get()}" # end_time = f"{end_year.get()}-{end_month.get()}-{end_day.get()} {end_hour.get()}:{end_minute.get()}:{end_second.get()}" # log_file = log_file_entry.get() # keywords_dict = { # &#39;motion_longsit:Wear not on Wrist&#39;: &#39;手表未佩戴在手腕上&#39;, # &#39;motion_longsit: suspect walking, statusCount&#39;: &#39;疑似正在行走,状态计数&#39;, # &#39;motion_longsit: no remind, in sleep or workout state&#39;: &#39;不提醒,处于睡眠或运动状态&#39;, # &#39;motion_longsit: enable is false&#39;: &#39;久坐提醒功能未启用&#39;, # &#39;motion_longsit:Motion remind report long sit&#39;: &#39;久坐提醒报告&#39;, # &#39;motion_fusion: config send&#39;: &#39;设备修改发送给APP的目标值&#39;, # &#39;motion_fusion: config&#39;: &#39;设备接收APP的目标值&#39;, # &#39;motion_data:sendAccNum&#39;: &#39;设备产生的数据(卡路里/10000)&#39;, # &#39;MotionDailyRevDataProc&#39;: &#39;设备接受来自app的数据(卡路里/10000)&#39;, # &#39;HealthModel::DealMotionDataReport totalstep&#39;: &#39;设备加APP的总热量&#39; # } # result = filter_logs_by_time_and_keywords(log_file, start_time, end_time, keywords_dict) # input_dir = os.path.dirname(log_file) # file_name = os.path.splitext(os.path.basename(log_file))[0] + "-output.txt" # output_file = os.path.join(input_dir, file_name) # try: # with open(output_file, &#39;w&#39;, encoding=&#39;utf-8&#39;) as out_file: # for log in result: # parts = log.split(",", 2) # first_line = f"{parts[0]},{parts[1]}" # second_line = parts[2] # out_file.write(first_line + &#39;\n&#39;) # out_file.write(second_line + &#39;\n&#39;) # messagebox.showinfo("完成", f"过滤完成,结果已保存到 {output_file}") # except Exception as e: # messagebox.showerror("错误", f"保存文件时出错:{e}") # # root = tk.Tk() # root.title("日志过滤工具") # root.geometry("600x350") # root.resizable(False, False) # # # 日志文件选择部分 # log_frame = ttk.Frame(root, padding="10") # log_frame.pack(pady=10) # # log_file_label = ttk.Label(log_frame, text="日志文件路径:") # log_file_label.grid(row=0, column=0, padx=5) # # log_file_entry = ttk.Entry(log_frame, width=50) # log_file_entry.grid(row=0, column=1, padx=5) # # select_file_button = ttk.Button(log_frame, text="选择文件", command=select_log_file) # select_file_button.grid(row=0, column=2, padx=5) # # # 时间选择部分 # time_frame = ttk.Frame(root, padding="10") # time_frame.pack(pady=10) # # # 开始时间 # start_time_label = ttk.Label(time_frame, text="开始时间:") # start_time_label.grid(row=0, column=0, padx=5) # # start_year = tk.StringVar() # start_year.set(datetime.now().year) # start_year_spinbox = ttk.Spinbox(time_frame, from_=2000, to=2100, textvariable=start_year, width=5) # start_year_spinbox.grid(row=0, column=1, padx=2) # # start_month = tk.StringVar() # start_month.set(datetime.now().month) # start_month_spinbox = ttk.Spinbox(time_frame, from_=1, to=12, textvariable=start_month, width=3) # start_month_spinbox.grid(row=0, column=2, padx=2) # # start_day = tk.StringVar() # start_day.set(datetime.now().day) # start_day_spinbox = ttk.Spinbox(time_frame, from_=1, to=31, textvariable=start_day, width=3) # start_day_spinbox.grid(row=0, column=3, padx=2) # # start_hour = tk.StringVar() # start_hour.set(0) # start_hour_spinbox = ttk.Spinbox(time_frame, from_=0, to=23, textvariable=start_hour, width=3) # start_hour_spinbox.grid(row=0, column=4, padx=2) # # start_minute = tk.StringVar() # start_minute.set(0) # start_minute_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=start_minute, width=3) # start_minute_spinbox.grid(row=0, column=5, padx=2) # # start_second = tk.StringVar() # start_second.set(0) # start_second_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=start_second, width=3) # start_second_spinbox.grid(row=0, column=6, padx=2) # # # 结束时间 # end_time_label = ttk.Label(time_frame, text="结束时间:") # end_time_label.grid(row=1, column=0, padx=5) # # end_year = tk.StringVar() # end_year.set(datetime.now().year) # end_year_spinbox = ttk.Spinbox(time_frame, from_=2000, to=2100, textvariable=end_year, width=5) # end_year_spinbox.grid(row=1, column=1, padx=2) # # end_month = tk.StringVar() # end_month.set(datetime.now().month) # end_month_spinbox = ttk.Spinbox(time_frame, from_=1, to=12, textvariable=end_month, width=3) # end_month_spinbox.grid(row=1, column=2, padx=2) # # end_day = tk.StringVar() # end_day.set(datetime.now().day) # end_day_spinbox = ttk.Spinbox(time_frame, from_=1, to=31, textvariable=end_day, width=3) # end_day_spinbox.grid(row=1, column=3, padx=2) # # end_hour = tk.StringVar() # end_hour.set(23) # end_hour_spinbox = ttk.Spinbox(time_frame, from_=0, to=23, textvariable=end_hour, width=3) # end_hour_spinbox.grid(row=1, column=4, padx=2) # # end_minute = tk.StringVar() # end_minute.set(59) # end_minute_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=end_minute, width=3) # end_minute_spinbox.grid(row=1, column=5, padx=2) # # end_second = tk.StringVar() # end_second.set(59) # end_second_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=end_second, width=3) # end_second_spinbox.grid(row=1, column=6, padx=2) # # # 运行按钮 # run_button = ttk.Button(root, text="运行过滤", command=run_filter) # run_button.pack(pady=20) # # root.mainloop() # # # import tkinter as tk # from tkinter import ttk, filedialog, messagebox # from datetime import datetime # import os # # def filter_logs_by_time_and_keywords(log_file, start_time, end_time, keyword_dict): # matched_logs = [] # start_time = datetime.strptime(start_time, &#39;%Y-%m-%d %H:%M:%S&#39;) # end_time = datetime.strptime(end_time, &#39;%Y-%m-%d %H:%M:%S&#39;) # try: # with open(log_file, &#39;r&#39;, encoding=&#39;utf-8&#39;) as file: # for line in file: # try: # time_str = line.split(&#39;,&#39;)[0] # log_time = datetime.strptime(time_str, &#39;%Y-%m-%d %H:%M:%S&#39;) # if start_time <= log_time <= end_time: # for keyword in keyword_dict.keys(): # if keyword.rfind(keyword) != -1 and keyword in line: # log_info = f"{time_str},{keyword_dict[keyword]},{line.strip()}" # matched_logs.append(log_info) # except ValueError: # continue # except FileNotFoundError: # messagebox.showerror("错误", "未找到指定的日志文件") # return matched_logs # # def select_log_file(): # file_path = filedialog.askopenfilename() # if file_path: # log_file_entry.delete(0, tk.END) # log_file_entry.insert(0, file_path) # # def run_filter(): # start_time = f"{start_year.get()}-{start_month.get()}-{start_day.get()} {start_hour.get()}:{start_minute.get()}:{start_second.get()}" # end_time = f"{end_year.get()}-{end_month.get()}-{end_day.get()} {end_hour.get()}:{end_minute.get()}:{end_second.get()}" # log_file = log_file_entry.get() # keywords_dict = {} # try: # with open(&#39;Keywords&#39;, &#39;r&#39;, encoding=&#39;utf-8&#39;) as file: # for line in file: # line = line.strip() # if line: # parts = line.split(&#39;:&#39;, 1) # if len(parts) == 2: # keywords_dict[parts[0]] = parts[1] # except FileNotFoundError: # messagebox.showerror("错误", "未找到 Keywords 文件") # result = filter_logs_by_time_and_keywords(log_file, start_time, end_time, keywords_dict) # input_dir = os.path.dirname(log_file) # file_name = os.path.splitext(os.path.basename(log_file))[0] + "-output.txt" # output_file = os.path.join(input_dir, file_name) # try: # with open(output_file, &#39;w&#39;, encoding=&#39;utf-8&#39;) as out_file: # for log in result: # parts = log.split(",", 2) # first_line = f"{parts[0]},{parts[1]}" # second_line = parts[2] # out_file.write(first_line + &#39;\n&#39;) # out_file.write(second_line + &#39;\n&#39;) # messagebox.showinfo("完成", f"过滤完成,结果已保存到 {output_file}") # except Exception as e: # messagebox.showerror("错误", f"保存文件时出错:{e}") # # root = tk.Tk() # root.title("日志过滤工具") # root.geometry("600x350") # root.resizable(False, False) # # # 日志文件选择部分 # log_frame = ttk.Frame(root, padding="10") # log_frame.pack(pady=10) # # log_file_label = ttk.Label(log_frame, text="日志文件路径:") # log_file_label.grid(row=0, column=0, padx=5) # # log_file_entry = ttk.Entry(log_frame, width=50) # log_file_entry.grid(row=0, column=1, padx=5) # # select_file_button = ttk.Button(log_frame, text="选择文件", command=select_log_file) # select_file_button.grid(row=0, column=2, padx=5) # # # 时间选择部分 # time_frame = ttk.Frame(root, padding="10") # time_frame.pack(pady=10) # # # 开始时间 # start_time_label = ttk.Label(time_frame, text="开始时间:") # start_time_label.grid(row=0, column=0, padx=5) # # start_year = tk.StringVar() # start_year.set(datetime.now().year) # start_year_spinbox = ttk.Spinbox(time_frame, from_=2000, to=2100, textvariable=start_year, width=5) # start_year_spinbox.grid(row=0, column=1, padx=2) # # start_month = tk.StringVar() # start_month.set(datetime.now().month) # start_month_spinbox = ttk.Spinbox(time_frame, from_=1, to=12, textvariable=start_month, width=3) # start_month_spinbox.grid(row=0, column=2, padx=2) # # start_day = tk.StringVar() # start_day.set(datetime.now().day) # start_day_spinbox = ttk.Spinbox(time_frame, from_=1, to=31, textvariable=start_day, width=3) # start_day_spinbox.grid(row=0, column=3, padx=2) # # start_hour = tk.StringVar() # start_hour.set(0) # start_hour_spinbox = ttk.Spinbox(time_frame, from_=0, to=23, textvariable=start_hour, width=3) # start_hour_spinbox.grid(row=0, column=4, padx=2) # # start_minute = tk.StringVar() # start_minute.set(0) # start_minute_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=start_minute, width=3) # start_minute_spinbox.grid(row=0, column=5, padx=2) # # start_second = tk.StringVar() # start_second.set(0) # start_second_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=start_second, width=3) # start_second_spinbox.grid(row=0, column=6, padx=2) # # # 结束时间 # end_time_label = ttk.Label(time_frame, text="结束时间:") # end_time_label.grid(row=1, column=0, padx=5) # # end_year = tk.StringVar() # end_year.set(datetime.now().year) # end_year_spinbox = ttk.Spinbox(time_frame, from_=2000, to=2100, textvariable=end_year, width=5) # end_year_spinbox.grid(row=1, column=1, padx=2) # # end_month = tk.StringVar() # end_month.set(datetime.now().month) # end_month_spinbox = ttk.Spinbox(time_frame, from_=1, to=12, textvariable=end_month, width=3) # end_month_spinbox.grid(row=1, column=2, padx=2) # # end_day = tk.StringVar() # end_day.set(datetime.now().day) # end_day_spinbox = ttk.Spinbox(time_frame, from_=1, to=31, textvariable=end_day, width=3) # end_day_spinbox.grid(row=1, column=3, padx=2) # # end_hour = tk.StringVar() # end_hour.set(23) # end_hour_spinbox = ttk.Spinbox(time_frame, from_=0, to=23, textvariable=end_hour, width=3) # end_hour_spinbox.grid(row=1, column=4, padx=2) # # end_minute = tk.StringVar() # end_minute.set(59) # end_minute_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=end_minute, width=3) # end_minute_spinbox.grid(row=1, column=5, padx=2) # # end_second = tk.StringVar() # end_second.set(59) # end_second_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=end_second, width=3) # end_second_spinbox.grid(row=1, column=6, padx=2) # # # 运行按钮 # run_button = ttk.Button(root, text="运行过滤", command=run_filter) # run_button.pack(pady=20) # # root.mainloop() import tkinter as tk from tkinter import ttk, filedialog, messagebox from datetime import datetime import os def filter_logs_by_time_and_keywords(log_file, start_time, end_time, keyword_dict): matched_logs = [] start_time = datetime.strptime(start_time, &#39;%Y-%m-%d %H:%M:%S&#39;) end_time = datetime.strptime(end_time, &#39;%Y-%m-%d %H:%M:%S&#39;) try: with open(log_file, &#39;r&#39;, encoding=&#39;utf-8&#39;) as file: for line in file: try: time_str = line.split(&#39;,&#39;)[0] log_time = datetime.strptime(time_str, &#39;%Y-%m-%d %H:%M:%S&#39;) if start_time <= log_time <= end_time: for keyword in keyword_dict.keys(): if keyword.rfind(keyword) != -1 and keyword in line: log_info = f"{time_str},{keyword_dict[keyword]},{line.strip()}" matched_logs.append(log_info) except ValueError: continue except FileNotFoundError: messagebox.showerror("错误", "未找到指定的日志文件") return matched_logs def select_log_file(): file_path = filedialog.askopenfilename() if file_path: log_file_entry.delete(0, tk.END) log_file_entry.insert(0, file_path) def run_filter(): start_time = f"{start_year.get()}-{start_month.get()}-{start_day.get()} {start_hour.get()}:{start_minute.get()}:{start_second.get()}" end_time = f"{end_year.get()}-{end_month.get()}-{end_day.get()} {end_hour.get()}:{end_minute.get()}:{end_second.get()}" log_file = log_file_entry.get() keywords_dict = {} try: # 修改此处,使用正确的文件名 with open(&#39;Keywords.txt&#39;, &#39;r&#39;, encoding=&#39;utf-8&#39;) as file: for line in file: line = line.strip() if line: parts = line.split(&#39;|||&#39;, 1) if len(parts) == 2: keywords_dict[parts[0]] = parts[1] except FileNotFoundError: messagebox.showerror("错误", "未找到 Keywords.txt 文件") result = filter_logs_by_time_and_keywords(log_file, start_time, end_time, keywords_dict) input_dir = os.path.dirname(log_file) file_name = os.path.splitext(os.path.basename(log_file))[0] + "-output.txt" output_file = os.path.join(input_dir, file_name) try: with open(output_file, &#39;w&#39;, encoding=&#39;utf-8&#39;) as out_file: for log in result: parts = log.split(",", 2) first_line = f"{parts[0]},{parts[1]}" second_line = parts[2] out_file.write(first_line + &#39;\n&#39;) out_file.write(second_line + &#39;\n&#39;) messagebox.showinfo("完成", f"过滤完成,结果已保存到 {output_file}") except Exception as e: messagebox.showerror("错误", f"保存文件时出错:{e}") root = tk.Tk() root.title("日志翻译工具") root.geometry("600x350") root.resizable(False, False) # 日志文件选择部分 log_frame = ttk.Frame(root, padding="10") log_frame.pack(pady=10) log_file_label = ttk.Label(log_frame, text="日志文件路径:") log_file_label.grid(row=0, column=0, padx=5) log_file_entry = ttk.Entry(log_frame, width=50) log_file_entry.grid(row=0, column=1, padx=5) select_file_button = ttk.Button(log_frame, text="选择文件", command=select_log_file) select_file_button.grid(row=0, column=2, padx=5) # 时间选择部分 time_frame = ttk.Frame(root, padding="10") time_frame.pack(pady=10) # 开始时间 start_time_label = ttk.Label(time_frame, text="开始时间:") start_time_label.grid(row=0, column=0, padx=5) start_year = tk.StringVar() start_year.set(datetime.now().year) start_year_spinbox = ttk.Spinbox(time_frame, from_=2000, to=2100, textvariable=start_year, width=5) start_year_spinbox.grid(row=0, column=1, padx=2) start_month = tk.StringVar() start_month.set(datetime.now().month) start_month_spinbox = ttk.Spinbox(time_frame, from_=1, to=12, textvariable=start_month, width=3) start_month_spinbox.grid(row=0, column=2, padx=2) start_day = tk.StringVar() start_day.set(datetime.now().day) start_day_spinbox = ttk.Spinbox(time_frame, from_=1, to=31, textvariable=start_day, width=3) start_day_spinbox.grid(row=0, column=3, padx=2) start_hour = tk.StringVar() start_hour.set(0) start_hour_spinbox = ttk.Spinbox(time_frame, from_=0, to=23, textvariable=start_hour, width=3) start_hour_spinbox.grid(row=0, column=4, padx=2) start_minute = tk.StringVar() start_minute.set(0) start_minute_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=start_minute, width=3) start_minute_spinbox.grid(row=0, column=5, padx=2) start_second = tk.StringVar() start_second.set(0) start_second_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=start_second, width=3) start_second_spinbox.grid(row=0, column=6, padx=2) # 结束时间 end_time_label = ttk.Label(time_frame, text="结束时间:") end_time_label.grid(row=1, column=0, padx=5) end_year = tk.StringVar() end_year.set(datetime.now().year) end_year_spinbox = ttk.Spinbox(time_frame, from_=2000, to=2100, textvariable=end_year, width=5) end_year_spinbox.grid(row=1, column=1, padx=2) end_month = tk.StringVar() end_month.set(datetime.now().month) end_month_spinbox = ttk.Spinbox(time_frame, from_=1, to=12, textvariable=end_month, width=3) end_month_spinbox.grid(row=1, column=2, padx=2) end_day = tk.StringVar() end_day.set(datetime.now().day) end_day_spinbox = ttk.Spinbox(time_frame, from_=1, to=31, textvariable=end_day, width=3) end_day_spinbox.grid(row=1, column=3, padx=2) end_hour = tk.StringVar() end_hour.set(23) end_hour_spinbox = ttk.Spinbox(time_frame, from_=0, to=23, textvariable=end_hour, width=3) end_hour_spinbox.grid(row=1, column=4, padx=2) end_minute = tk.StringVar() end_minute.set(59) end_minute_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=end_minute, width=3) end_minute_spinbox.grid(row=1, column=5, padx=2) end_second = tk.StringVar() end_second.set(59) end_second_spinbox = ttk.Spinbox(time_frame, from_=0, to=59, textvariable=end_second, width=3) end_second_spinbox.grid(row=1, column=6, padx=2) # 运行按钮 run_button = ttk.Button(root, text="运行过滤", command=run_filter) run_button.pack(pady=20) root.mainloop() import tkinter as tk from tkinter import ttk, filedialog, messagebox from datetime import datetime import os import re # 从 Keywords.txt 加载关键词字典 def load_keywords(keyword_file=&#39;Keywords.txt&#39;): keyword_dict = {} if not os.path.exists(keyword_file): return None try: with open(keyword_file, &#39;r&#39;, encoding=&#39;utf-8&#39;) as f: for line in f: line = line.strip() if line and &#39;:&#39; in line: k, v = line.split(&#39;:&#39;, 1) keyword_dict[k.strip()] = v.strip() except Exception as e: print(f"加载关键词文件出错: {e}") return None return keyword_dict # 构建标准格式的时间字符串(自动补零) def build_time_string(year, month, day, hour, minute, second): try: y = int(year) mon = int(month) d = int(day) h = int(hour) m = int(minute) s = int(second) # 自动补零并返回标准格式 return f"{y:04d}-{mon:02d}-{d:02d} {h:02d}:{m:02d}:{s:02d}" except ValueError: raise ValueError("时间字段必须为整数") # 根据时间范围和关键字过滤日志 def filter_logs_by_time_and_keywords(log_file, start_time, end_time, keyword_dict): matched_logs = [] try: start_dt = datetime.strptime(start_time, &#39;%Y-%m-%d %H:%M:%S&#39;) end_dt = datetime.strptime(end_time, &#39;%Y-%m-%d %H:%M:%S&#39;) except ValueError as ve: messagebox.showerror("错误", f"时间格式无效: {ve}") return [] # 匹配日志行中的时间戳(行首可能有 YYYY-MM-DD HH:MM:SS) time_pattern = re.compile(r&#39;^(\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2})&#39;) try: with open(log_file, &#39;r&#39;, encoding=&#39;utf-8&#39;) as file: for line_num, line in enumerate(file, 1): line = line.strip(&#39;\n&#39;) match = time_pattern.search(line) if not match: continue # 跳过无时间戳的行 time_str = match.group(1) try: log_time = datetime.strptime(time_str, &#39;%Y-%m-%d %H:%M:%S&#39;) except ValueError: continue # 时间格式错误跳过 if start_dt <= log_time <= end_dt: for keyword, description in keyword_dict.items(): if keyword in line: log_info = (f"{time_str},{description}", line) matched_logs.append(log_info) break # 避免重复添加同一行 except FileNotFoundError: messagebox.showerror("错误", "未找到指定的日志文件") return [] except Exception as e: messagebox.showerror("错误", f"读取日志文件时发生异常: {e}") return [] return matched_logs # 选择日志文件 def select_log_file(): file_path = filedialog.askopenfilename( title="选择日志文件", filetypes=[("Log files", "*.log"), ("Text files", "*.txt"), ("All files", "*.*")] ) if file_path: log_file_entry.delete(0, tk.END) log_file_entry.insert(0, file_path) # 创建时间选择组件 def create_time_picker(parent, row, column_start, label_text, default_year=None, default_month=None, default_day=None, default_hour=None, default_minute=None, default_second=None): now = datetime.now() ttk.Label(parent, text=label_text).grid(row=row, column=column_start, sticky=tk.W, padx=(0, 5)) year = tk.StringVar(value=str(default_year or now.year)) month = tk.StringVar(value=str(default_month or now.month)) day = tk.StringVar(value=str(default_day or now.day)) hour = tk.StringVar(value=str(default_hour or 0)) minute = tk.StringVar(value=str(default_minute or 0)) second = tk.StringVar(value=str(default_second or 0)) ttk.Spinbox(parent, from_=2000, to=2100, textvariable=year, width=6).grid(row=row, column=column_start + 1, padx=2) ttk.Spinbox(parent, from_=1, to=12, textvariable=month, width=4).grid(row=row, column=column_start + 2, padx=2) ttk.Spinbox(parent, from_=1, to=31, textvariable=day, width=4).grid(row=row, column=column_start + 3, padx=2) ttk.Spinbox(parent, from_=0, to=23, textvariable=hour, width=4).grid(row=row, column=column_start + 4, padx=2) ttk.Spinbox(parent, from_=0, to=59, textvariable=minute, width=4).grid(row=row, column=column_start + 5, padx=2) ttk.Spinbox(parent, from_=0, to=59, textvariable=second, width=4).grid(row=row, column=column_start + 6, padx=2) return year, month, day, hour, minute, second # 执行过滤操作 def run_filter(): # 获取时间 try: start_time = build_time_string( start_year.get(), start_month.get(), start_day.get(), start_hour.get(), start_minute.get(), start_second.get() ) end_time = build_time_string( end_year.get(), end_month.get(), end_day.get(), end_hour.get(), end_minute.get(), end_second.get() ) except ValueError as ve: messagebox.showerror("错误", f"时间输入不合法:{ve}") return # 检查时间逻辑 if start_time > end_time: messagebox.showwarning("警告", "开始时间不能晚于结束时间!") return # 获取日志文件路径 log_file = log_file_entry.get().strip() if not log_file or not os.path.isfile(log_file): messagebox.showerror("错误", "请指定有效的日志文件") return # 加载关键词 keyword_dict = load_keywords() if keyword_dict is None or len(keyword_dict) == 0: messagebox.showerror("错误", "Keywords.txt 文件不存在或为空") return # 执行过滤 result = filter_logs_by_time_and_keywords(log_file, start_time, end_time, keyword_dict) if not result: messagebox.showinfo("提示", "未找到符合条件的日志条目") return # 输出路径 input_dir = os.path.dirname(log_file) base_name = os.path.splitext(os.path.basename(log_file))[0] output_file = os.path.join(input_dir, f"{base_name}-output.txt") # 写入结果 try: with open(output_file, &#39;w&#39;, encoding=&#39;utf-8&#39;) as out_file: for time_line, log_line in result: out_file.write(f"{time_line}\n") out_file.write(f"{log_line}\n\n") messagebox.showinfo("完成", f"过滤完成!共找到 {len(result)} 条记录\n已保存至:\n{output_file}") except Exception as e: messagebox.showerror("错误", f"无法保存文件:{e}") # ========== GUI 主程序 ========== root = tk.Tk() root.title("🔍 日志翻译工具") root.geometry("700x380") root.resizable(False, False) # --- 日志文件选择区 --- log_frame = ttk.Frame(root, padding="10") log_frame.pack(pady=10, fill=tk.X) ttk.Label(log_frame, text="日志文件:").grid(row=0, column=0, sticky=tk.W) log_file_entry = ttk.Entry(log_frame, width=55) log_file_entry.grid(row=0, column=1, padx=5) ttk.Button(log_frame, text="📁 浏览", command=select_log_file).grid(row=0, column=2, padx=5) # --- 时间选择区 --- time_frame = ttk.Frame(root, padding="10") time_frame.pack(pady=10, fill=tk.X) start_year, start_month, start_day, start_hour, start_minute, start_second = create_time_picker( time_frame, 0, 0, "开始时间:", default_hour=0, default_minute=0, default_second=0 ) end_year, end_month, end_day, end_hour, end_minute, end_second = create_time_picker( time_frame, 1, 0, "结束时间:", default_hour=23, default_minute=59, default_second=59 ) # --- 执行按钮 --- ttk.Button(root, text="▶️ 日志翻译", command=run_filter).pack(pady=20) # 启动主循环 root.mainloop()
最新发布
12-05
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值