import cv2
from siamese import Siamese
import pandas as pd
import math
import math
import numpy as np
import math
import matplotlib.pyplot as plt
from PIL import Image
import glob
from siamese import Siamese
import openpyxl as op
import numpy as np
import torch
import torchvision
import matplotlib.pyplot as plt
import time
# 确定比遍历步长,输出相似度最大时的遍历位置,找到相似度最大时的图像块起点坐标
def FindMax(step):
# 裁剪大小
w, h = 300, 300
# 此处设置横向和纵向移动步长一致,遍历起点为(0,0)
x = 0
y = 0
# list 为图片相似度列表,XY为每次遍历起点坐标
list = []
XY = []
# 大图宽纵尺寸减去小图宽纵尺寸除以移动步长并向下取整,得出共需要挪动多少步
Sw = (image_Big.size[0] - image_1.size[0]) // step
Sh = (image_Big.size[1] - image_1.size[1]) // step
# print("横向移动步数:{0},纵向移动步数{1}".format(Sw, Sh))
# 小图在大图中遍历,并输出图像相似度list及其小图起点坐标XY
for i in range(Sw):
for j in range(Sh):
x = 0 + step * i
y = 0 + step * j
image_2 = image_Big.crop((x, y, x + w, y + h))
probability = model.detect_image(image_1, image_2).cpu().numpy()
list.append(probability[0])
XY.append((x, y))
# 找到相似度最大所在的位置,并输出这时的起点坐标, 输出最大相似度及其对应的起点位置
Max_where = np.where(list == np.max(list))[0]
Max_where_XY = XY[int(Max_where[0 ])]
return Max_where_XY
# 找到匹配块和匹配快像素坐标,并输出标注位置后的图像image_Big2
def Match(Max_where_XY, image_Big):
Match_point1 = Max_where_XY
Match_point2 = (Max_where_XY[0] + 300, Max_where_XY[1] + 300)
# print("左上角起点坐标:{0} 右下角终点坐标:{1}".format(first_point, last_point))
image_Big = cv2.rectangle(np.array(image_Big), Match_point1, Match_point2, (0, 255, 0), 5)
# print("中心点X:{0},中心点Y{1}:".format(mid_X, mid_Y))
right_point2 = right_point1[0]+300, right_point1[1]+300
image_Big2 = cv2.rectangle(image_Big, right_point1, right_point2, (0, 0, 255), 5)
return image_Big2, Match_point1
# 计算IOU,输入匹配起点位置Match_point1,真实起点位置 right_point1,大小300*300已定,输出IOU
def make_IOU(Match_point1,right_point1):
# 匹配终点位置,真实终点位置
Match_point2 = Match_point1[0]+300, Match_point1[1]+300
right_point2 = right_point1[0]+300, right_point1[1]+300
# 匹配点相对于正确点:左上
if right_point1[0]-300 <= Match_point1[0] <= right_point1[0] and right_point1[1]-300 <= Match_point1[1] <= right_point1[1]:
(inter_x1, inter_y1) = (right_point1[0], right_point1[1])
(inter_x2, inter_y2) = (Match_point2[0], Match_point2[1])
# 匹配点相对于正确点:左下
elif right_point1[0]-300 <= Match_point1[0] <= right_point1[0] and right_point1[1] <= Match_point1[1] <= right_point1[1]+300:
(inter_x1, inter_y1) = (right_point1[0], right_point1[1] + 300)
(inter_x2, inter_y2) = (Match_point1[0] + 300, Match_point1[1])
# 匹配点相对于正确点:右下
elif right_point1[0] <= Match_point1[0] <= right_point2[0] and right_point1[1] <= Match_point1[1] <= right_point2[1]:
(inter_x1, inter_y1) = (Match_point1[0], Match_point1[1])
(inter_x2, inter_y2) = (right_point2[0], right_point2[1])
# 可能需要改
# 匹配点相对于正确点:右上
elif right_point1[0] <= Match_point1[0] <= right_point2[0] and right_point1[1]-300 <= Match_point1[1] <= right_point1[1]:
(inter_x1, inter_y1) = (Match_point1[0], Match_point1[1] + 300)
(inter_x2, inter_y2) = (right_point1[0] + 300, right_point1[1])
else:
(inter_x1, inter_y1)=(0,0)
(inter_x2, inter_y2)=(inter_x1, inter_y1)
# 计算交集矩形面积
# print('inter_x1-inter_x2:',inter_x1-inter_x2)
# print('inter_y1-inter_y2:',inter_y1-inter_y2)
Inter_area = abs(inter_x1 - inter_x2) * abs(inter_y1 - inter_y2)
# print('Inter_area',Inter_area)
# 并集面积
Total_area = 300 * 300 * 2
Union_area = Total_area - Inter_area
# 计算IOU交集面积/并集面积
IOU = Inter_area / Union_area
return IOU
# 以下将只在本模块中运行
if __name__ == "__main__":
model = Siamese()
# 记录实时图名字,中心点距离,面积交并比
for i in range(9, 10, 1):
img_name1 = []
D = []
list_IOU = []
for img in range(-20, 35, 5):
# 循环读取两个文件夹下的图片
# 读入两张图片,并遍历图片,找出相似度最高所在的位置
# 小图image_1,大图image_Big
image_1 = f'C:/Users/Lenovo/Desktop/test/chapter{i}/{img}.png'
img_name = img
img_name1.append(img_name)
image_1 = Image.open(image_1)
# 输入大图路径
k = "%03d" % (i+1)
image_Big = fr'C:\Users\Lenovo\Desktop\test源60-sort/{k}.png'
image_Big = Image.open(image_Big)
# 正确Start_X Start_Y起点坐标
xl = op.load_workbook(r'C:\Users\Lenovo\Desktop\test60\test中心点.xlsx')
names = xl.sheetnames
sheet = xl[names[0]]
mid_X = sheet.cell(row=i+2, column=2).value
mid_Y = sheet.cell(row=i+2, column=3).value
print('mid_X, mid_Y:', mid_X, mid_Y)
right_point1 = mid_X - 150,mid_Y - 150
# 确定遍历步长,找出相似度最高的位置坐标
tis1 = time.perf_counter()
Max_where_XY=FindMax(100)
# 在图上画出匹配出的区域与正确区域
image_Big2, Match_point1 = Match(Max_where_XY, image_Big)
# 计算中心点位置d,此处和起点坐标距离一样
d = math.sqrt(pow((Match_point1[0]-right_point1[0]),2)+pow((Match_point1[1]-right_point1[1]),2))
print('中心点距离:',d)
D.append(d)
# 计算重合面积IOU
IOU = make_IOU(Match_point1, right_point1)
print('面积交并比IOU:', IOU)
list_IOU.append(IOU)
tis2 = time.perf_counter()
print(tis2 - tis1)
# plt.subplot(1, 2, 1)
# # 解决中文显示问题
# plt.rcParams['font.sans-serif'] = ['SimHei']
# plt.rcParams['axes.unicode_minus'] = False
# plt.title('实时图',fontsize=20)
# plt.imshow(image_1)
#
# plt.axis('off')
# plt.subplot(1, 2, 2)
plt.rcParams['font.sans-serif'] = ['SimHei']
plt.rcParams['axes.unicode_minus'] = False
plt.title(f'旋转角度{img}°', fontsize=20, y=-0.1)
# plt.savefig(f'C:/Users/Lenovo/Desktop/IOU/{img}.png')
plt.imshow(image_Big2)
# plt.text(-12, -12, 'Similarity:%.3f' % output, ha='center', va='bottom', fontsize=11)
# plt.text(x,y,string,fontsize=15,verticalalignment="top",horizontalalignment="right")
plt.axis('off')
plt.show()
# print('D:',D)
# print('img_name1:',img_name1)
# print('list_IOU',list_IOU)
# 将将图片名,中心点距离,面积交并比写入excel
for n in range(1, len(D) + 1):
bg = op.load_workbook(r"D&IOU.xlsx") # 应先将excel文件放入到工作目录下
sheet = bg["Sheet1"] # “Sheet1”表示将数据写入到excel文件的sheet1下
row_num = n # 写进第几行
# sheet.cell(n, 1, img_name1[n-1]) # image1的名字
sheet.cell(n, 5, D[n - 1]) # image2的名字
sheet.cell(n, 6, list_IOU[n - 1]) # 准确率
bg.save("D&IOU.xlsx") # 对文件进行保存
find_location
最新推荐文章于 2024-09-17 23:15:58 发布