Object Detection With Pre-trained YOLO

1849 views May 18, 2024

ဒီနေ့မှာတော့ object detection ကို train ပြီးသား yolov3 model ကိုသုံးပြီး object detection ပုံစံ လုပ်ကြပါမယ်။

မှတ်ချက်။။ဒီထဲက code တချို့သည် google ခေါက်ရင် အလွယ်တကူတွေ့နိုင်ပါတယ်။နားလည်ရလွယ်အောင် အနည်းငယ်ပြင်ထားပြီး ပြန်လည်ရှင်းပြပေးချင်းဖြစ်ပါတယ်။Opencv,computer vision basic ကိုသိထားရပါမယ်။

အောက်ကလင့်ကို click ပြီးဒေါင်းလော့လုပ်ပါ

https://s3pyrobocity.s3-us-west-2.amazonaws.com/media/models/yolo.zip

Project Structure

  • object_detect
    • detect.py
    • yolo
      • coco.names
      • yolov3.cfg
      • yolov3.weights

Object detect ဆိုတဲ့ folder ထဲမှာ detect.py ရယ် yolo ဆိုတဲ့ folder ရှိပါမယ်။yolo folder ထဲမှာတော့ coco.names ဆိုတဲ့ object labels တွေရယ် config file ရယ် model weight file ရယ်ရှိနေပါမယ်။

အဓိက ကြည့်ရမှာကတော့ detect.py ပါ။အဲ့တော့ detect.py ထဲမှာ အောက်က code တွေစရေးရအောင်

# import the necessary packages
import numpy as np
import imutils
import argparse
import time
import cv2
import os
 
 
ap = argparse.ArgumentParser()
ap.add_argument("-i", "--image", required=True,
	help="path to input image")
ap.add_argument("-y", "--yolo", required=True,
	help="base path to YOLO directory")
ap.add_argument("-c", "--confidence", type=float, default=0.5,
	help="minimum probability to filter weak detections")
ap.add_argument("-t", "--threshold", type=float, default=0.3,
	help="threshold when applying non-maxima suppression")
args = vars(ap.parse_args())

အပေါ်ကတိုင်း လိုအပ်တဲ့ packages တွေ import လုပ်ပြီး လိုအပ်တဲ့ argument များ ဖြစ်တဲ့ image ရယ် yolo model ယူဖို့ yolo ရယ် object detect လုပ်လို့ ဘယ်လောက် confidence ရှိမှ ယူမယ်ဆိုတာရယ် object detect လုပ်တဲ့အခါ အမှားနည်းအောင် non-maxma supression အတွက် value ရယ် ကိုရေးထားပါတယ်။

labelsPath = os.path.sep.join([args["yolo"], "coco.names"])
LABELS = open(labelsPath).read().strip().split("\n")
 
 
np.random.seed(42)
COLORS = np.random.randint(0, 255, size=(len(LABELS), 3),
	dtype="uint8")
 
 
 
weightsPath = os.path.sep.join([args["yolo"], "yolov3.weights"])
configPath = os.path.sep.join([args["yolo"], "yolov3.cfg"])

coco.names file မှာ trained ထားတဲ့ object labels တွေရှိပါတယ်။အဲ့ labels တွေကို read လိုက်ပြီး random colors များယူလိုက်ပါတယ်။ဥပမာ ကားဆို အရောင်တမျိုး မြင်းဆို အရောင်တမျိုး အဲ့လိုမျိုးလေး ဖြစ်အောင် ကိုယ်တိုင်သတ်မှတ်နေရင် အလုပ်ရှုပ်လို့ random color ယူလိုက်ပါတယ်။ပြီးရင်တော့ model weight ရယ် config path ရယ်ကိုယူလိုက်ပါတယ်။

print("[INFO] loading YOLO from disk...")
net = cv2.dnn.readNetFromDarknet(configPath, weightsPath)
 
 
image = cv2.imread(args["image"])
image = imutils.resize(image,width=800)
(H, W) = image.shape[:2]
 
ln = net.getLayerNames()
ln = [ln[i[0] - 1] for i in net.getUnconnectedOutLayers()]
 
 
blob = cv2.dnn.blobFromImage(image, 1 / 255.0, (416, 416),
	swapRB=True, crop=False)
net.setInput(blob)
start = time.time()
layerOutputs = net.forward(ln)
end = time.time()
print("[INFO] YOLO took {:.6f} seconds".format(end - start))

Opencv ရဲ့နောက်ပိုင်း version မှာပါလာတယ့် dnn module ကိုသုံးပြီး model ကို load လုပ်လိုက်ပါတယ်။ပြီးရင်တော့ image ကို read ပြီး detect အဆင်ပြေအောင် နည်းနည်းလေး ချုံ့လိုက်ပါတယ်။Optional ပါ။မလုပ်လဲအဆင်ပြေပါတယ်။ပြီးရင်တော့ network layers တွေကိုယူထားလိုက်ပါတယ်။image ကို တန်းပြီး network ထဲ ထည့်လိုက်လို့မရပါဘူး။အဲ့တော့ feature လေးတွေဖြစ်တဲ့ yolo လက်ခံနိုင်တဲ့ size ထဲက 416×416 နဲ့ blob ယူပြီး ပြီးတော့မှ network ထဲ forward လုပ်လိုက်တာပါ။

boxes = []
confidences = []
classIDs = []
 
 
for output in layerOutputs:
	
	for detection in output:
		scores = detection[5:]
		classID = np.argmax(scores)
		confidence = scores[classID]
	
		if confidence > args["confidence"]:
			box = detection[0:4] * np.array([W, H, W, H])
			(centerX, centerY, width, height) = box.astype("int")
 
			# use the center (x, y)-coordinates to derive the top
			# and and left corner of the bounding box
			x = int(centerX - (width / 2))
			y = int(centerY - (height / 2))
 
			boxes.append([x, y, int(width), int(height)])
			confidences.append(float(confidence))
			classIDs.append(classID)
 
 
idxs = cv2.dnn.NMSBoxes(boxes, confidences, args["confidence"],args["threshold"])
 
 
if len(idxs) > 0:
	for i in idxs.flatten():
		(x, y) = (boxes[i][0], boxes[i][1])
		(w, h) = (boxes[i][2], boxes[i][3])
 
		
		color = [int(c) for c in COLORS[classIDs[i]]]
		cv2.rectangle(image, (x, y), (x + w, y + h), color, 2)
		text = "{}: {:.4f}".format(LABELS[classIDs[i]], confidences[i])
		cv2.putText(image, text, (x, y - 5), cv2.FONT_HERSHEY_SIMPLEX,
			0.5, color, 2)
 
cv2.imshow("Image", image)
cv2.waitKey(0)

အပေါ်ကတော့ output ထဲကနေ rectangle ဆွဲလို့ရအောင် လုပ်တာလေးပါပဲ။detect လုပ်တာ ဘယ်လောက်ထိ confidence ရှိလဲ ဥပမာ ၄၀% လောက်ပဲမှန်တာမျိုးတို့ဆို ကျွန်တော်တို့က မယူတာအကောင်းဆုံးပဲမို့ argument ပေးတုန်းက 50% အထက်မှ ယူအောင်စစ်ထားတာလေးပဲသတိပြုရမှာပါ။

နောက်တစ်ဆင့်ကတော့ detect လုပ်လို့ရတဲ့ object တွေရဲ့ indexes တွေကို ယူပြီး loop ပတ်တာ rectangle ဆွဲလို့ရအောင် boxes ထဲကနေ သက်ဆိုင်ရာ x,y,w,h တွေပြန်ယူပြီး rectangle ဆွဲလိုက်ပါတယ်။ပြီးရင်တော့ image ကို show လုပ်လိုက်ပါတယ်။

python detect.py --image ~/Pictures/chincoteague_ponies.jpg.653x0_q80_crop-smart.jpg --yolo yolo/

အပေါ်က command နဲ့ –image နောက်က ကိုယ် detect လုပ်မဲ့ image ကို ထည့်ပြီး run ကြည့်လိုက်ပါ။အားလုံးအဆင်ပြေပါစေ။

Output