evaluate_tool.py 2.4 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. import numpy as np
  2. def calculate_ciou(box1, box2):
  3. """计算CIoU,假设box格式为[x1, y1, x2, y2]"""
  4. x1, y1, x2, y2 = box1
  5. x1g, y1g, x2g, y2g = box2
  6. # 求交集面积
  7. xi1, yi1 = max(x1, x1g), max(y1, y1g)
  8. xi2, yi2 = min(x2, x2g), min(y2, y2g)
  9. inter_area = max(0, xi2 - xi1) * max(0, yi2 - yi1)
  10. # 求各自面积
  11. box_area = (x2 - x1) * (y2 - y1)
  12. boxg_area = (x2g - x1g) * (y2g - y1g)
  13. # 求并集面积
  14. union_area = box_area + boxg_area - inter_area
  15. # 求IoU
  16. iou = inter_area / union_area
  17. # 求CIoU额外项
  18. cw = max(x2, x2g) - min(x1, x1g)
  19. ch = max(y2, y2g) - min(y1, y1g)
  20. c2 = cw ** 2 + ch ** 2
  21. rho2 = ((x1 + x2 - x1g - x2g) ** 2 + (y1 + y2 - y1g - y2g) ** 2) / 4
  22. ciou = iou - (rho2 / c2)
  23. return ciou
  24. def calculate_iou(box1, box2):
  25. # 计算IoU的基础方法
  26. inter_x_min = max(box1[0], box2[0])
  27. inter_y_min = max(box1[1], box2[1])
  28. inter_x_max = min(box1[2], box2[2])
  29. inter_y_max = min(box1[3], box2[3])
  30. inter_area = max(0, inter_x_max - inter_x_min) * max(0, inter_y_max - inter_y_min)
  31. box1_area = (box1[2] - box1[0]) * (box1[3] - box1[1])
  32. box2_area = (box2[2] - box2[0]) * (box2[3] - box2[1])
  33. union_area = box1_area + box2_area - inter_area
  34. iou = inter_area / union_area if union_area > 0 else 0
  35. return iou
  36. def calculate_giou(box1, box2):
  37. iou = calculate_iou(box1, box2)
  38. # 计算最小外包围矩形
  39. c_x_min = min(box1[0], box2[0])
  40. c_y_min = min(box1[1], box2[1])
  41. c_x_max = max(box1[2], box2[2])
  42. c_y_max = max(box1[3], box2[3])
  43. c_area = (c_x_max - c_x_min) * (c_y_max - c_y_min)
  44. giou = iou - (
  45. c_area - (box1[2] - box1[0]) * (box1[3] - box1[1]) - (box2[2] - box2[0]) * (box2[3] - box2[1])) / c_area
  46. return giou
  47. def calculate_diou(box1, box2):
  48. iou = calculate_iou(box1, box2)
  49. # 计算中心点的距离
  50. box1_center = [(box1[0] + box1[2]) / 2, (box1[1] + box1[3]) / 2]
  51. box2_center = [(box2[0] + box2[2]) / 2, (box2[1] + box2[3]) / 2]
  52. center_distance = np.sum(np.square(np.array(box1_center) - np.array(box2_center)))
  53. # 计算最小外包围矩形的对角线距离
  54. c_x_min = min(box1[0], box2[0])
  55. c_y_min = min(box1[1], box2[1])
  56. c_x_max = max(box1[2], box2[2])
  57. c_y_max = max(box1[3], box2[3])
  58. c_diag_distance = np.sum(np.square(np.array([c_x_max, c_y_max]) - np.array([c_x_min, c_y_min])))
  59. diou = iou - center_distance / c_diag_distance
  60. return diou