import torch import sys,os sys.path.extend(['/home/thsw2/WJ/src/yolov5/segutils']) from core.models.bisenet import BiSeNet from torchvision import transforms import cv2,glob import numpy as np from core.models.dinknet import DinkNet34 import matplotlib.pyplot as plt import time class SegModel(object): def __init__(self, nclass=2,weights=None,modelsize=512,device='cuda:0'): #self.args = args self.model = BiSeNet(nclass) #self.model = DinkNet34(nclass) checkpoint = torch.load(weights) self.modelsize = modelsize self.model.load_state_dict(checkpoint['model']) self.device = device self.model= self.model.to(self.device) '''self.composed_transforms = transforms.Compose([ transforms.Normalize(mean=(0.335, 0.358, 0.332), std=(0.141, 0.138, 0.143)), transforms.ToTensor()]) ''' self.mean = (0.335, 0.358, 0.332) self.std = (0.141, 0.138, 0.143) def eval(self,image): time0 = time.time() imageH,imageW,imageC = image.shape image = self.preprocess_image(image) time1 = time.time() self.model.eval() image = image.to(self.device) with torch.no_grad(): output = self.model(image) time2 = time.time() pred = output.data.cpu().numpy() pred = np.argmax(pred, axis=1)[0]#得到每行 time3 = time.time() pred = cv2.resize(pred.astype(np.uint8),(imageW,imageH)) time4 = time.time() outstr= 'pre-precess:%.1f ,infer:%.1f ,post-precess:%.1f ,post-resize:%.1f, total:%.1f \n '%( self.get_ms(time1,time0),self.get_ms(time2,time1),self.get_ms(time3,time2),self.get_ms(time4,time3),self.get_ms(time4,time0) ) #print('pre-precess:%.1f ,infer:%.1f ,post-precess:%.1f ,post-resize:%.1f, total:%.1f '%( self.get_ms(time1,time0),self.get_ms(time2,time1),self.get_ms(time3,time2),self.get_ms(time4,time3),self.get_ms(time4,time0) )) return pred,outstr def get_ms(self,t1,t0): return (t1-t0)*1000.0 def preprocess_image(self,image): time0 = time.time() image = cv2.resize(image,(self.modelsize,self.modelsize)) time0 = time.time() image = image.astype(np.float32) image /= 255.0 image[:,:,0] -=self.mean[0] image[:,:,1] -=self.mean[1] image[:,:,2] -=self.mean[2] image[:,:,0] /= self.std[0] image[:,:,1] /= self.std[1] image[:,:,2] /= self.std[2] image = cv2.cvtColor( image,cv2.COLOR_RGB2BGR) #image -= self.mean #image /= self.std image = np.transpose(image, ( 2, 0, 1)) image = torch.from_numpy(image).float() image = image.unsqueeze(0) return image def get_ms(t1,t0): return (t1-t0)*1000.0 def get_largest_contours(contours): areas = [cv2.contourArea(x) for x in contours] max_area = max(areas) max_id = areas.index(max_area) return max_id if __name__=='__main__': image_url = '/home/thsw2/WJ/data/THexit/val/images/DJI_0645.JPG' nclass = 2 weights = '../weights/segmentation/BiSeNet/checkpoint.pth' segmodel = SegModel(nclass=nclass,weights=weights) image_urls=glob.glob('/home/thsw2/WJ/data/THexit/val/images/*') out_dir ='../runs/detect/exp2-seg';os.makedirs(out_dir,exist_ok=True) for image_url in image_urls[0:1]: image_url = '/home/thsw2/WJ/data/THexit/val/images/54(199).JPG' image_array0 = cv2.imread(image_url) pred = segmodel.eval(image_array0 ) #plt.figure(1);plt.imshow(pred); #plt.show() binary0 = pred.copy() time0 = time.time() contours, hierarchy = cv2.findContours(binary0,cv2.RETR_TREE,cv2.CHAIN_APPROX_SIMPLE) max_id = -1 if len(contours)>0: max_id = get_largest_contours(contours) binary0[:,:] = 0 print(contours[0].shape,contours[1].shape,contours[0]) cv2.fillPoly(binary0, [contours[max_id][:,0,:]], 1) time1 = time.time() #num_labels,_,Areastats,centroids = cv2.connectedComponentsWithStats(binary0,connectivity=4) time2 = time.time() cv2.drawContours(image_array0,contours,max_id,(0,255,255),3) time3 = time.time() out_url='%s/%s'%(out_dir,os.path.basename(image_url)) ret = cv2.imwrite(out_url,image_array0) time4 = time.time() print('image:%s findcontours:%.1f ms , connect:%.1f ms ,draw:%.1f save:%.1f'%(os.path.basename(image_url),get_ms(time1,time0),get_ms(time2,time1), get_ms(time3,time2),get_ms(time4,time3), ) ) plt.figure(0);plt.imshow(pred) plt.figure(1);plt.imshow(image_array0) plt.figure(2);plt.imshow(binary0) plt.show() #print(out_url,ret)