Gần đây, tôi muốn xây dựng một hệ thống để phát hiện các đối tượng trong một số dữ liệu hình ảnh. Vì vậy, tôi bắt đầu tìm hiểu Mạng thần kinh chuyển đổi dựa trên khu vực (RCNN) và đó là sự phát triển, mô hình CNN đã có sẵn, v.v. Đối với tôi, nó rất khó nắm bắt vì có nhiều thuật ngữ mới xuất hiện trong các bài đọc tham khảo Vì vậy, để khắc phục điều này, tôi đã xây dựng tất cả các thuật ngữ đặc biệt xuất hiện trong bài đọc tham khảo của mình. - CNN là một mạng thần kinh có một lớp đặc biệt là lớp tích chập (và lớp tổng hợp). Trong mô hình CNN thông thường, lớp cuối cùng thường là lớp dày đặc
- RCNN là một CNN đặc biệt và là thế hệ mô hình RCNN đầu tiên sử dụng thuật toán tìm kiếm chọn lọc để đề xuất một số hộp giới hạn bao phủ đối tượng mà chúng tôi muốn phát hiện. Đầu tiên, chúng tôi áp dụng thuật toán tìm kiếm có chọn lọc để lấy một số hộp giới hạn (đề xuất khu vực). Và sau đó, đưa các khu vực được đề xuất đó vào mô hình CNN
- Fast-RCNN là thế hệ thứ hai của mô hình RCNN. Mô hình này nhanh hơn RCNN (Fast-RCNN > RCNN). Hình ảnh đầu vào ban đầu được đưa vào mô hình CNN để thực hiện trích xuất tính năng. Sau đó, chúng tôi sử dụng tìm kiếm có chọn lọc để nhận đề xuất khu vực và đưa chúng vào Lớp Vùng quan tâm (RoI) để cố định kích thước ma trận của chúng (khu vực được đề xuất có nhiều hình dạng có thể). Sau khi chúng có kích thước cố định, hãy đưa chúng vào lớp dày đặc để dự đoán lớp đó và xác định hộp giới hạn
- Faster-RCNN là thế hệ thứ ba của mô hình RCNN. Mô hình này nhanh hơn Fast-RCNN (Faster-RCNN > Fast-RCNN > RCNN). Mô hình này loại bỏ việc sử dụng các thuật toán tìm kiếm chọn lọc chậm. Để nhận đề xuất khu vực, chúng tôi sử dụng Mạng đề xuất khu vực (RPN)
- Trích xuất tính năng là để đạt được đầu ra của lớp cuối cùng của mô hình CNN thông thường trước lớp dày đặc (hoặc lớp trước đó)
- Bản đồ tính năng là ma trận kết quả từ trích xuất tính năng
- Tìm kiếm chọn lọc là một thuật toán đề xuất hoạt động bằng cách phân đoạn quá mức hình ảnh dựa trên cường độ của pixel bằng phương pháp phân đoạn dựa trên biểu đồ
- Lớp RoI là lớp tổng hợp đặc biệt để làm cho kích thước vùng được đề xuất khớp với lớp dày đặc tiếp theo của mạng thần kinh
- RPN là một mạng thần kinh có 2 đầu. Một để phân loại nền hoặc tiền cảnh và cái còn lại để xác định vùng hộp giới hạn
- Anchor là trung tâm của khu vực được đề xuất trong Faster-RCNN
- Giao lộ trên Liên minh (IoU) là thước đo đánh giá các đề xuất khu vực. Nó được hình thành dưới dạng diện tích chồng lấn / diện tích hợp nhất
- Non Maximum Suppression là một cách để đảm bảo một đối tượng chỉ được phát hiện một lần. Điều này được thực hiện bằng cách áp dụng một số ngưỡng
Tôi sẽ bổ sung danh sách này trong tương lai nếu tôi tìm thấy các thuật ngữ mới liên quan đến phát hiện đối tượng trong Deep Learning Người giới thiệu https. // hướng tới khoa học dữ liệu. com/r-cnn-fast-r-cnn-faster-r-cnn-yolo-object-detection-algorithms-36d53571365e, truy cập ngày 3 tháng 2 năm 2019 https. //www. họcopencv. com/selective-search-for-object-detection-cpp-python/, truy cập ngày 3 tháng 2 năm 2019 https. //thử nghiệm. com/blog/2018/01/18/faster-r-cnn-down-the-rabbit-hole-of-modern-object-detection/, truy cập ngày 3 tháng 2 năm 2019 Khi làm việc trong Object Detection, đã bao giờ bạn hí hửng tải mô hình đã được huấn luyện sẵn về rồi phát hiện ra mô hình không có đối tượng mà bạn cần? Đối với những trường hợp này thì có lẽ không còn cách nào khác, chúng ta phải huấn luyện mô hình cấu hình với tệp dữ liệu mới. May mắn cho chúng ta là việc huấn luyện mô hình trên tập dữ liệu mới ngày càng trở nên dễ dàng Hãy cùng tìm hiểu các bước đào tạo mô hình Phát hiện đối tượng cho một đối tượng mới, cụ thể là gấu trúc (phát hiện gấu trúc) dựa trên YOLOv5 trong bài hôm nay. Mình chọn đối tượng này, một phần là mình thích gấu trúc, một phần nữa là mình chưa thấy mô hình nào có đối tượng này. Hơn nữa, các bước xây dựng mô hình hoàn toàn có thể áp dụng cho bất kỳ đối tượng nào khác Sơ lược về YOLOv5YOLOv5 là một mô hình Object Detection thuộc họ mô hình YOLO. Nếu các bạn chưa biết thì 3 phiên bản YOLO đầu tiên được phát triển bởi Joseph Redmon. Sau đó, Alexey Bochkovskiy cho ra mắt YOLOv4 với sự cải thiện cả về tốc độ cũng như độ chính xác. Và rồi YOLOv5 đã được công bố gần đây với những so sánh ban đầu cho thấy mức độ chính xác tương đương với YOLOv4 và có tốc độ nhanh hơn khi thực hiện dự đoán (tuy nhiên vẫn có rất nhiều hoài nghi về mức độ tin cậy của những so sánh Khác với các phiên bản tiền nhiệm, YOLOv5 được phát triển dựa trên PyTorch thay vì DarkNet. Đây là một điểm cộng không nhỏ đối với YOLOv5 vì PyTorch phổ biến hơn rất nhiều, điều này đồng nghĩa với việc sẽ có nhiều tài liệu và hướng dẫn cho chúng tôi tham khảo về mô hình này Cá nhân mình đánh giá cấu trúc YOLOv5 không có nhiều thay đổi quá lớn nhưng lại được phát triển trên PyTorch và có hướng dẫn rất chi tiết và đầy đủ. Làm đó, mình chọn YOLOv5 cho bài thực hành hôm nay Chuẩn bị dữ liệuTrước hết chúng ta cần phải có dữ liệu ảnh và nhãn (images & label). Dữ liệu đối với mô hình cũng giống như những viên gạch để xây dựng nhà, không có dữ liệu thì không xây dựng được mô hình nào cả Tập hợp ảnhCó vài cách để thu thập ảnh cho việc huấn luyện mô hình - Tìm trên Open Images Dataset, đây là tập hợp hơn 9 triệu ảnh với 6000 nhóm khác nhau
- Tìm kiếm với công cụ tìm kiếm (Google, Bing, …) với lưu ý cần kiểm tra kỹ năng bản quyền sử dụng ảnh
- Trích xuất các khung hình từ Video
- Tự chụp ảnh
Trong bài viết hôm nay, mình sử dụng thư viện năm mươi mốt để tải ảnh từ Open Images Dataset 1
2
3
4
5
6
7
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
Dữ liệu tải về sẽ có 3 thư mục, mình chỉ lấy ảnh thư mục ảnh dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
3 để thực hiện việc gán nhãn ở bước tiếp theo.
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
Gán nhãnMình sử dụng thư viện nhãnImg cho việc gán nhãn và mất khoảng hơn 1h để gán nhãn cho khoảng 130 ảnh. (Bạn nào biết công cụ nào tiện hơn thì chia sẻ cho mình và mọi người biết nhé) Bước gán nhãn này thường tốn nhiều thời gian và không thú vị lắm, nhưng tự nhủ không có gạch thì không xây được nhà nên cố gắng thử Gán nhãn với LabelImgCác bạn lưu ý chọn định dạng YOLO khi xuất các tệp để đảm bảo định dạng đúng cho việc huấn luyện mô hình sau này To the style of the format of YOLO (Ultralytics)Mỗi ảnh sẽ có một nhãn (tệp dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
4) tương ứng để chứa thông tin về đường bao của đối tượng- Mỗi dòng chứa thông tin của một đối tượng
- Mỗi dòng có 5 giá trị chứa thông tin về đối tượng và đường bao. object, to speed center x, to speed trung tâm y, width, length
- Lưu ý là đường bao đã được chuẩn hóa về khoảng
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
5 (đây là yêu cầu của mô hình YOLO)
Dưới đây là ví dụ về nhãn và tệp chứa thông tin về đối tượng Nhãn và tệp chứa tên các nhóm đối tượngSắp xếp thư mục ảnh và nhãnSau khi đã có ảnh và nhãn, chúng ta có thể sắp xếp các thư mục như sau custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
- Cấu hình tệp của tệp dữ liệu
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
6 chứa đường dẫn đến thư mục ảnh và đối tượng thông tin________số 8 - Tệp cấu hình của mô hình
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
7 chứa thông tin cấu trúc mạng, ở đây chúng ta sử dụng cấu trúc mô hình YOLOv5s (cỡ nhỏ) với mục tiêu rút ngắn thời gian huấn luyện và kích thước mô hình. Lưu ý là chúng ta hoàn toàn có thể sử dụng cấu trúc khác, ví dụ như YOLOv5m, YOLOv5l, YOLOv5x từ YOLOv5 hoặc một cấu trúc mới do chúng ta tự thiết kếdataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
0 - Thư mục
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
8 chứa ảnh và nhãn được sử dụng để huấn luyện mô hìnhdataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
2- Thư mục
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
9 và .
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
0 chứa ảnh và nhãn tương ứng - Ảnh và nhãn được chia thành 2 thư mục
.
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
1 và .
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
2 (dùng để huấn luyện và kiểm tra mô hình) - Thư mục
dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
9 còn có 1 thư mục con .
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
4 chứa ảnh dùng để kiểm tra chất lượng mô hình
Huấn luyện mô hìnhCài đặt thư viện liên quanTải YOLOv5 từ GitHub và cài đặt các thư viện liên quan dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
9Lưu ý là chúng ta cần YOLOv5 ở cùng thư mục với .
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
5 ở trêndataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
1Huấn luyệnCác bước chuẩn bị đã hoàn thành, giờ luyện tập trở nên rất đơn giản dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
2.
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
6. image size (decal mode).
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
7. số ảnh dùng để huấn luyện trong mỗi lần.
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
8. training number for all the image in file data .
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
1dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
3. path to configure file of data filecustom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
1. đường dẫn đến file cấu hình của mô hìnhcustom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
2. đường dẫn đến tệp custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
3 chứa các liên kết giữa các nơ-ron (đến custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
4 là để luyện tập từ đầu)custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
5. tên thư mục để lưu cấu hìnhcustom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
6. use memory buffer to training nhanh hơn
Kết quảSử dụng custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
7 để kiểm tra kết quả của bài tập huấn luyện (các số chỉ thay đổi như thế nào sau mỗi custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
8)dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
0dataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
1Khi tập luyện kết thúc, có 2 trọng lượng tệp mô hình được lưu lại - Mô hình tốt nhất.
custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
9 (tốt nhất chỉ dựa trên số Độ chính xác trung bình trên tập kiểm tra) - Cuối cùng mô hình.
# relative paths from folder yolov5
# .
# ├── custom_dataset
# └── yolov5
train: ../custom_dataset/images_and_labels/images/train/
val: ../custom_dataset/images_and_labels/images/valid/
# number of classes
nc: 1
# class names
names: ['panda']
0
Dự đoán với mô hình được huấn luyệndataset = fiftyone.zoo.load_zoo_dataset(
"open-images-v6",
split="train",
label_types=["detections"],
classes=["Panda"],
max_samples=250,
)
2custom_dataset
├── custom_dataset.yaml
├── custom_model.yaml
└── images_and_labels
2. trọng lượng tệp được sử dụng để dự đoán.
├── data
│ ├── 02a4749df3d7a0c9.jpg
│ ├── 0b5547d4aa16e365.jpg
│ ...
├── labels
│ └── detections.csv
└── metadata
├── classes.csv
├── hierarchy.json
└── image_ids.csv
6. image size (decal mode)# relative paths from folder yolov5
# .
# ├── custom_dataset
# └── yolov5
train: ../custom_dataset/images_and_labels/images/train/
val: ../custom_dataset/images_and_labels/images/valid/
# number of classes
nc: 1
# class names
names: ['panda']
3. độ tin cậy# relative paths from folder yolov5
# .
# ├── custom_dataset
# └── yolov5
train: ../custom_dataset/images_and_labels/images/train/
val: ../custom_dataset/images_and_labels/images/valid/
# number of classes
nc: 1
# class names
names: ['panda']
4. path to the image directory
Kết quả dự đoán được lưu tại thư mục # relative paths from folder yolov5
# .
# ├── custom_dataset
# └── yolov5
train: ../custom_dataset/images_and_labels/images/train/
val: ../custom_dataset/images_and_labels/images/valid/
# number of classes
nc: 1
# class names
names: ['panda']
5 (hoặc exp2, 3,… tùy vào số lần chúng ta chạy dự đoán với # relative paths from folder yolov5
# .
# ├── custom_dataset
# └── yolov5
train: ../custom_dataset/images_and_labels/images/train/
val: ../custom_dataset/images_and_labels/images/valid/
# number of classes
nc: 1
# class names
names: ['panda']
6)Kết quả dự đoán trên ảnh mới từ tập tin thử nghiệmGoogle Colab and dataMình đã chuẩn bị sẵn một Google Colab Notebook để tiện cho việc tham khảo. Các bạn hoàn toàn có thể sử dụng dữ liệu của mình để sử dụng với notebook này (chỉ cần chuẩn bị đúng cấu hình của file là ổn định) Bên cạnh đó, mình lưu tệp cấu trúc sắc nét với nhãn ở Panda ML Blog Github để các bạn có thể thực hiện các hành động quen thuộc với các bước xây dựng mô hình khi chưa có dữ liệu trong tay pauseBài hôm nay đã giới thiệu đến các bạn các bước huấn luyện mô hình Phát hiện đối tượng dựa trên YOLOv5. Có thể bước khoảng thời gian ngắn nhất là bước tìm ảnh phù hợp và gắn nhãn cho ảnh. Ngoài ra các bước huấn luyện và dự đoán, khá dễ dàng. Trong thực tế cũng vậy,bước chuẩn bị dữ liệu (chuẩn bị dữ liệu) thường cũng là bước thời gian nhất Với tệp dữ liệu hơn 100 ảnh, mình khá hài lòng với mô hình đã được huấn luyện khi mô hình này cho kết quả tương đối ổn. Hy vọng là với bài hướng dẫn này, các bạn cũng sẽ rèn luyện được những mô hình thú vị cho riêng mình
|