מדריך לזיהוי אובייקטים ב-Python

המשימה 'זיהוי אובייקטים' ב-MediaPipe מאפשרת לזהות את הנוכחות והמיקום של כמה סוגים של אובייקטים. בהוראות האלה מוסבר איך להשתמש במשימה Object Detector ב-Python. דוגמת הקוד שמתוארת בהוראות האלה זמינה ב-GitHub.

אתם יכולים לראות את המשימה הזו בפעולה בהדגמה באינטרנט. מידע נוסף על היכולות, המודלים והאפשרויות להגדרה של המשימה הזו זמין בסקירה הכללית.

קוד לדוגמה

קוד הדוגמה לזיהוי אובייקטים כולל הטמעה מלאה של המשימה הזו ב-Python. הקוד הזה יעזור לכם לבדוק את המשימה הזו ולהתחיל לפתח אפליקציה משלכם לסיווג טקסט. אתם יכולים להציג, להריץ ולערוך את קוד הדוגמה של גלאי העצמים רק באמצעות דפדפן האינטרנט.

אם אתם מטמיעים את הכלי לזיהוי אובייקטים ב-Raspberry Pi, תוכלו להיעזר באפליקציית הדוגמה ל-Raspberry Pi.

הגדרה

בקטע הזה מתוארים השלבים העיקריים להגדרת סביבת הפיתוח ופרויקטי הקוד, באופן ספציפי לשימוש ב-Object Detector. מידע כללי על הגדרת סביבת הפיתוח לשימוש במשימות של MediaPipe, כולל דרישות לגרסאות הפלטפורמה, זמין במדריך ההגדרה ל-Python.

חבילות

כדי לבצע את המשימה 'זיהוי אובייקטים', צריך את חבילת ה-pip של mediapipe. אפשר להתקין את החבילות הנדרשות באמצעות הפקודות הבאות:

$ python -m pip install mediapipe

יבוא

כדי לגשת לפונקציות של משימת Object Detector, מייבאים את הכיתות הבאות:

import mediapipe as mp
from mediapipe.tasks import python
from mediapipe.tasks.python import vision

דגם

כדי לבצע את המשימה 'זיהוי אובייקטים' ב-MediaPipe, נדרש מודל מאומן שתואם למשימה הזו. למידע נוסף על המודלים המאומנים הזמינים לזיהוי אובייקטים, ראו הקטע 'מודלים' בסקירה הכללית של המשימה.

בוחרים מודל ומורידים אותו, ולאחר מכן שומרים אותו בספרייה מקומית:

model_path = '/absolute/path/to/lite-model_efficientdet_lite0_detection_metadata_1.tflite'

משתמשים בפרמטר model_asset_path של האובייקט BaseOptions כדי לציין את הנתיב של המודל שבו רוצים להשתמש. דוגמה לקוד מופיעה בקטע הבא.

יצירת המשימה

משתמשים בפונקציה create_from_options כדי ליצור את המשימה. הפונקציה create_from_options מקבלת אפשרויות תצורה, כולל מצב ריצה, אזור גיאוגרפי להצגת שמות, מספר תוצאות מקסימלי, ערך סף ביטחון, רשימת ההיתרים של הקטגוריה ורשימת הדחייה. אם לא תגדירו אפשרות תצורה, המשימה תשתמש בערך ברירת המחדל. מידע נוסף על אפשרויות ההגדרה זמין בקטע אפשרויות הגדרה.

המשימה 'זיהוי אובייקטים' תומכת בכמה סוגי נתוני קלט: תמונות סטילס, קובצי וידאו וסטרימינג של וידאו בשידור חי. בוחרים את הכרטיסייה שמתאימה לסוג נתוני הקלט כדי לראות איך יוצרים את המשימה ומריצים את ההסקה.

תמונה

import mediapipe as mp

BaseOptions = mp.tasks.BaseOptions
ObjectDetector = mp.tasks.vision.ObjectDetector
ObjectDetectorOptions = mp.tasks.vision.ObjectDetectorOptions
VisionRunningMode = mp.tasks.vision.RunningMode

options = ObjectDetectorOptions(
    base_options=BaseOptions(model_asset_path='/path/to/model.tflite'),
    max_results=5,
    running_mode=VisionRunningMode.IMAGE)

with ObjectDetector.create_from_options(options) as detector:
  # The detector is initialized. Use it here.
  # ...
    

וידאו

import mediapipe as mp

BaseOptions = mp.tasks.BaseOptions
ObjectDetector = mp.tasks.vision.ObjectDetector
ObjectDetectorOptions = mp.tasks.vision.ObjectDetectorOptions
VisionRunningMode = mp.tasks.vision.RunningMode

options = ObjectDetectorOptions(
    base_options=BaseOptions(model_asset_path='/path/to/model.tflite'),
    max_results=5,
    running_mode=VisionRunningMode.VIDEO)

with ObjectDetector.create_from_options(options) as detector:
  # The detector is initialized. Use it here.
  # ...
    

שידור חי

import mediapipe as mp

BaseOptions = mp.tasks.BaseOptions
DetectionResult = mp.tasks.components.containers.detections.DetectionResult
ObjectDetector = mp.tasks.vision.ObjectDetector
ObjectDetectorOptions = mp.tasks.vision.ObjectDetectorOptions
VisionRunningMode = mp.tasks.vision.RunningMode

def print_result(result: DetectionResult, output_image: mp.Image, timestamp_ms: int):
    print('detection result: {}'.format(result))

options = ObjectDetectorOptions(
    base_options=BaseOptions(model_asset_path='/path/to/model.tflite'),
    running_mode=VisionRunningMode.LIVE_STREAM,
    max_results=5,
    result_callback=print_result)

with ObjectDetector.create_from_options(options) as detector:
  # The detector is initialized. Use it here.
  # ...
    

דוגמה מלאה ליצירת גלאי אובייקטים לשימוש בתמונה מופיעה בדוגמת הקוד.

אפשרויות הגדרה

למשימה הזו יש את אפשרויות התצורה הבאות לאפליקציות Python:

שם האפשרות תיאור טווח ערכים ערך ברירת מחדל
running_mode הגדרת מצב ההפעלה של המשימה. יש שלושה מצבים:

IMAGE: המצב להזנת תמונה אחת.

VIDEO: המצב של פריימים מפוענחים של סרטון.

LIVE_STREAM: המצב של סטרימינג בשידור חי של נתוני קלט, למשל ממצלמה. במצב הזה, צריך להפעיל את resultListener כדי להגדיר מאזין שיקבל את התוצאות באופן אסינכרוני.
{IMAGE, VIDEO, LIVE_STREAM} IMAGE
display_names הגדרת השפה של התוויות לשימוש בשמות התצוגה שסופקו במטא-נתונים של מודל המשימה, אם הם זמינים. ברירת המחדל היא en לאנגלית. אפשר להוסיף תוויות מותאמות לשוק המקומי למטא-נתונים של מודל מותאם אישית באמצעות TensorFlow Lite Metadata Writer API קוד לוקאל en
max_results מגדיר את המספר המקסימלי האופציונלי של תוצאות זיהוי עם הדירוג הגבוה ביותר שיוחזר. מספרים חיוביים -1 (כל התוצאות מוצגות)
score_threshold הגדרת הסף של ציון התחזית, שמבטל את הסף שצוין במטא-נתונים של המודל (אם יש כזה). תוצאות מתחת לערך הזה נדחות. כל ערך צף לא מוגדר
category_allowlist הגדרת רשימה אופציונלית של שמות קטגוריות מותרים. אם הערך לא ריק, תוצאות הזיהוי ששם הקטגוריה שלהן לא נמצא בקבוצה הזו יוסר. המערכת מתעלמת משמות קטגוריות כפולים או לא מוכרים. האפשרות הזו לא תואמת לאפשרות category_denylist, ושימוש בשתיהן גורם לשגיאה. מחרוזות כלשהן לא מוגדר
category_denylist הגדרת רשימה אופציונלית של שמות קטגוריות אסורים. אם הערך לא ריק, תוצאות הזיהוי ששם הקטגוריה שלהן נמצא בקבוצה הזו יסוננו. המערכת מתעלמת משמות קטגוריות כפולים או לא מוכרים. האפשרות הזו לא תואמת לאפשרות category_allowlist, ושימוש בשתיהן גורם לשגיאה. מחרוזות כלשהן לא מוגדר

הכנת הנתונים

מכינים את הקלט כקובץ תמונה או כמערך numpy, ואז ממירים אותו לאובייקט mediapipe.Image. אם הקלט הוא קובץ וידאו או שידור חי ממצלמת אינטרנט, אפשר להשתמש בספרייה חיצונית כמו OpenCV כדי לטעון את הפריימים של הקלט כמערכי numpy.

הדוגמאות הבאות ממחישות איך להכין נתונים לעיבוד לכל אחד מסוגי הנתונים הזמינים:

תמונה

import mediapipe as mp

# Load the input image from an image file.
mp_image = mp.Image.create_from_file('/path/to/image')

# Load the input image from a numpy array.
mp_image = mp.Image(image_format=mp.ImageFormat.SRGB, data=numpy_image)
    

וידאו

import mediapipe as mp

# Use OpenCV’s VideoCapture to load the input video.

# Load the frame rate of the video using OpenCV’s CV_CAP_PROP_FPS
# You’ll need it to calculate the timestamp for each frame.

# Loop through each frame in the video using VideoCapture#read()

# Convert the frame received from OpenCV to a MediaPipe’s Image object.
mp_image = mp.Image(image_format=mp.ImageFormat.SRGB, data=numpy_frame_from_opencv)
    

שידור חי

import mediapipe as mp

# Use OpenCV’s VideoCapture to start capturing from the webcam.

# Create a loop to read the latest frame from the camera using VideoCapture#read()

# Convert the frame received from OpenCV to a MediaPipe’s Image object.
mp_image = mp.Image(image_format=mp.ImageFormat.SRGB, data=numpy_frame_from_opencv)
    

הרצת המשימה

אפשר לקרוא לאחת מפונקציות הזיהוי כדי להפעיל את ההסקות. המשימה Object Detector תחזיר את האובייקטים שזוהו בתמונה או בפריים של הקלט.

תמונה

# Perform object detection on the provided single image.
detection_result = detector.detect(mp_image)
    

וידאו

# Calculate the timestamp of the current frame
frame_timestamp_ms = 1000 * frame_index / video_file_fps

# Perform object detection on the video frame.
detection_result = detector.detect_for_video(mp_image, frame_timestamp_ms)
    

שידור חי

# Send the latest frame to perform object detection.
# Results are sent to the `result_callback` provided in the `ObjectDetectorOptions`.
detector.detect_async(mp_image, frame_timestamp_ms)
    

דוגמה מלאה להפעלת 'זיהוי אובייקטים' בתמונה מפורטת בדוגמת הקוד.

שימו לב לנקודות הבאות:

  • כשמריצים את הקוד במצב וידאו או במצב של שידור חי, צריך לספק למשימה של זיהוי האובייקטים גם את חותמת הזמן של פריים הקלט.
  • כשמריצים את המודל בתמונה או בסרטון, המשימה של 'זיהוי אובייקטים' תמנע את המשך הפעילות של השרשור הנוכחי עד שיסתיים עיבוד התמונה או הפריים של הקלט.
  • כשמריצים את המשימה במצב של שידור חי, היא לא חוסמת את השרשור הנוכחי אלא חוזרת מיד. הוא יפעיל את מאזין התוצאות שלו עם תוצאת הזיהוי בכל פעם שהוא יסיים לעבד מסגרת קלט. אם פונקציית הזיהוי מופעלת בזמן שהמשימה של 'זיהוי אובייקטים' עסוקה בעיבוד של פריים אחר, המערכת תתעלם מפריים הקלט החדש.

טיפול בתוצאות והצגתן

לאחר הפעלת ההסקה, המשימה Object Detector מחזירה אובייקט ObjectDetectionResult שמתאר את האובייקטים שהיא מצאה בתמונה הקלט.

בהמשך מוצגת דוגמה לנתוני הפלט של המשימה הזו:

ObjectDetectorResult:
 Detection #0:
  Box: (x: 355, y: 133, w: 190, h: 206)
  Categories:
   index       : 17
   score       : 0.73828
   class name  : dog
 Detection #1:
  Box: (x: 103, y: 15, w: 138, h: 369)
  Categories:
   index       : 17
   score       : 0.73047
   class name  : dog

בתמונה הבאה מוצגת תצוגה חזותית של הפלט של המשימה:

שני כלבים שמודגשים באמצעות תיבות גבול

בקוד לדוגמה של 'זיהוי אובייקטים' מוסבר איך להציג את תוצאות הזיהוי שהוחזרו מהמשימה. פרטים נוספים זמינים בקוד לדוגמה.