import matplotlib
matplotlib.use('TkAgg') # 在导入pyplot之前设置
import matplotlib.pyplot as plt
import matplotlib.patches as patches
import numpy as np
import matplotlib.font_manager as fmdef find_and_set_chinese_font():"""动态查找并设置中文字体"""# 中文字体关键词chinese_keywords = ['SimHei', 'SimSun', 'Microsoft', '微软雅黑', '黑体', '宋体', '楷体', '仿宋']# 获取所有可用字体font_list = fm.findSystemFonts()font_names = [fm.FontProperties(fname=f).get_name() for f in font_list]# 查找中文字体chinese_fonts = []for keyword in chinese_keywords:for font_name in font_names:if keyword.lower() in font_name.lower():chinese_fonts.append(font_name)if chinese_fonts:# 设置第一个找到的中文字体plt.rcParams['font.sans-serif'] = chinese_fonts[:3] # 取前3个print(f"找到中文字体: {chinese_fonts[:3]}")else:# 如果找不到中文字体,使用Arial Unicode MSplt.rcParams['font.sans-serif'] = ['Arial Unicode MS', 'DejaVu Sans']print("使用跨平台字体 Arial Unicode MS")# 解决负号显示问题plt.rcParams['axes.unicode_minus'] = Falsereturn chinese_fontsdef visualize_enclosing_box():"""可视化最小闭包区域的计算过程"""fig, ax = plt.subplots(1, 1, figsize=(10, 8))# 定义两个框的坐标 [x1, y1, x2, y2]box_a = [2, 3, 6, 7] # 预测框 (蓝色)box_b = [4, 1, 9, 5] # 真实框 (红色)# 计算最小闭包区域enclosing_box = [min(box_a[0], box_b[0]), # x1min(box_a[1], box_b[1]), # y1max(box_a[2], box_b[2]), # x2max(box_a[3], box_b[3]) # y2]# 绘制预测框 (蓝色)rect_a = patches.Rectangle((box_a[0], box_a[1]),box_a[2] - box_a[0],box_a[3] - box_a[1],linewidth=2,edgecolor='blue',facecolor='lightblue',alpha=0.5,label='预测框 A')# 绘制真实框 (红色)rect_b = patches.Rectangle((box_b[0], box_b[1]),box_b[2] - box_b[0],box_b[3] - box_b[1],linewidth=2,edgecolor='red',facecolor='lightcoral',alpha=0.5,label='真实框 B')# 绘制最小闭包区域 (绿色虚线)rect_c = patches.Rectangle((enclosing_box[0], enclosing_box[1]),enclosing_box[2] - enclosing_box[0],enclosing_box[3] - enclosing_box[1],linewidth=2,edgecolor='green',facecolor='none',linestyle='--',label='最小闭包区域 C')# 添加到图中ax.add_patch(rect_a)ax.add_patch(rect_b)ax.add_patch(rect_c)# 标注框的角点# 预测框角点ax.plot([box_a[0], box_a[2], box_a[2], box_a[0], box_a[0]],[box_a[1], box_a[1], box_a[3], box_a[3], box_a[1]],'bo', markersize=4, label='预测框顶点')# 真实框角点ax.plot([box_b[0], box_b[2], box_b[2], box_b[0], box_b[0]],[box_b[1], box_b[1], box_b[3], box_b[3], box_b[1]],'ro', markersize=4, label='真实框顶点')# 闭包区域角点ax.plot([enclosing_box[0], enclosing_box[2], enclosing_box[2], enclosing_box[0], enclosing_box[0]],[enclosing_box[1], enclosing_box[1], enclosing_box[3], enclosing_box[3], enclosing_box[1]],'go', markersize=4, label='闭包区域顶点')# 添加坐标标注ax.text(box_a[0] + 0.2, box_a[1] + 0.2, f'A({box_a[0]},{box_a[1]})', fontsize=9, color='blue')ax.text(box_a[2] - 1.2, box_a[3] - 0.3, f'A({box_a[2]},{box_a[3]})', fontsize=9, color='blue')ax.text(box_b[0] + 0.2, box_b[1] + 0.2, f'B({box_b[0]},{box_b[1]})', fontsize=9, color='red')ax.text(box_b[2] - 1.2, box_b[3] - 0.3, f'B({box_b[2]},{box_b[3]})', fontsize=9, color='red')ax.text(enclosing_box[0] + 0.2, enclosing_box[1] + 0.2, f'C({enclosing_box[0]},{enclosing_box[1]})',fontsize=9, color='green')ax.text(enclosing_box[2] - 1.2, enclosing_box[3] - 0.3, f'C({enclosing_box[2]},{enclosing_box[3]})',fontsize=9, color='green')# 设置图形属性ax.set_xlim(0, 11)ax.set_ylim(0, 9)ax.set_xlabel('X坐标')ax.set_ylabel('Y坐标')ax.set_title('最小闭包区域计算示例')ax.legend()ax.grid(True, alpha=0.3)plt.tight_layout()plt.show()# 打印计算结果print("=== 最小闭包区域计算结果 ===")print(f"预测框 A: [{box_a[0]}, {box_a[1]}, {box_a[2]}, {box_a[3]}]")print(f"真实框 B: [{box_b[0]}, {box_b[1]}, {box_b[2]}, {box_b[3]}]")print(f"最小闭包区域 C: [{enclosing_box[0]}, {enclosing_box[1]}, {enclosing_box[2]}, {enclosing_box[3]}]")print(f"闭包区域面积: {(enclosing_box[2] - enclosing_box[0]) * (enclosing_box[3] - enclosing_box[1])}")# 应用设置
chinese_fonts = find_and_set_chinese_font()
# 运行可视化示例
visualize_enclosing_box()
