Đếm xe máy bằng thuật toán Background Subtraction

Sử dụng thuật toán Background Subtraction để đếm lượt xe vào bãi. Hình ảnh quay từ tầng hầm bãi xe tại quận 11. Đếm xe máy bằng thuật toán Background Subtraction là phương pháp hiệu quả nhất. Bởi vì xe có rất nhiều loại mà chỉ cần biết “có xe hay không” chứ không cần xác định chính xác vị trí.

Thuật toán được implement sẵn trong opencv, sử dụng thêm 1 số hàm đơn giản để nâng độ chính xác.




Thuật toán

Chương trình xử lý theo từng frame, chỉ cần extract frame trong video rồi đưa vào xử lý.



Đây là hình ảnh input, là 1 frame của video
bgs_0



Dùng thuật toán BGS ta được kết quả
bgs_1



Ảnh sau khi xử lý bị nhiễu khá nhiều, do đó áp dụng 1 chút blur để khử nhiễu
bgs_2



Sau đó phân ngưỡng rồi tìm blob, đếm số lượng pixel của blob đó rồi xuất kết quả
bgs_3

Lưu ý là hình minh họa lấy từ frame “lý tưởng”, thuật toán chưa hoàn toàn chính xác 100%. Các bạn chạy thử sẽ thấy cũng khá nhiều sai số chưa áp dụng thương mại được.

Thuật toán này sai trong các trường hợp: đối tượng có cùng màu background, hình ảnh nhòe,… Cách khắc phục là tìm thuật toán tốt hơn hoặc thay đổi camera, hệ thống chiếu sáng.

Download source code

Source code thuật toán đếm xe máy viết bằng C++, build bằng Visual Studio 2015

Các bạn download về sửa đường dẫn file video trong file bin\BikeCounterConfig.ini
BikeCounter.zip (34MB)

Download video

Video gốc dùng để test thuật toán
bike_counter_10min.mp4 (61 MB)

9 thoughts on “Đếm xe máy bằng thuật toán Background Subtraction

  1. bool TGMTbgs::LoadConfig()
    {
    m_minWidth = GetTGMTConfig()->ReadValueInt(INI_SECTION, “min_width”);
    m_minHeight = GetTGMTConfig()->ReadValueInt(INI_SECTION, “min_height”);
    m_blurSize = GetTGMTConfig()->ReadValueInt(INI_SECTION, “blur_size”);
    m_minPoints = GetTGMTConfig()->ReadValueInt(INI_SECTION, “min_points”);
    m_maxPoints = GetTGMTConfig()->ReadValueInt(INI_SECTION, “max_points”);
    m_debug = GetTGMTConfig()->ReadValueBool(INI_SECTION, “debug”);
    m_dilate = GetTGMTConfig()->ReadValueInt(INI_SECTION, “dilate”);
    m_erode = GetTGMTConfig()->ReadValueInt(INI_SECTION, “erode”);
    return true;
    }
    ad ơi mấy biến như m_blurSize, m_dilate, m_erode là gì vậy ạ. với lại tính những biến này như thế nào vậy ạ? e xem mà không hiểu những thông số này.

Leave a Reply