Алгоритм OpenCV замедляется без причины - PullRequest
0 голосов
/ 01 марта 2019

В данный момент я работаю над проектом, который ищет образец в видеопотоке и постоянно проверяет его.Но через некоторое время (иногда несколько секунд, иногда несколько минут) он просто перестает работать.Нет обнаружения, нет видеопотока.Я проверил свой процессор, а также пробовал разные разрешения.Но это все еще не работает правильно.

#include "pch.h"
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include <iostream>
#include <array>
#include <stdio.h>
#include "opencv2/core/mat.hpp"

using namespace std;
using namespace cv;

/// Create a flag, used for nearly everything
int flag = 0;
int i = 0;

/// BlackPixel counter
float blackPixel;

/// Localizing the best match with minMaxLoc
double minVal, maxVal; 
Point minLoc, maxLoc, matchLoc;

/// Punkte für drawMatch
Point middle_x, middle_y;

/// Creating picture Matrix
Mat image_input, image_template, image_display, image_object;

/// Create the result matrix
int result_cols, result_rows;

/// Test Inputs
Mat pictureTest;
Mat objectTest;



string intToString(int number) {

    std::stringstream ss;
    ss << number;
    return ss.str();

}


void drawMatch(Mat object, Mat scene, vector<Point> match_centers)
{
    for (size_t i = 0; i < match_centers.size(); i++)
    {
        /// middle of template at X
        middle_x = Point((object.cols / 2) + match_centers[i].x, match_centers[i].y);

        /// middle of template at Y
        middle_y = Point(match_centers[i].x, match_centers[i].y + (object.rows / 2));

        /// Zeichnet Rechteck um Match
        rectangle(scene, Point(match_centers[i].x, match_centers[i].y), Point(match_centers[i].x + object.cols, match_centers[i].y + object.rows), Scalar(0, 255, 0), 2);

        /// Zeigt das Ergebnis des Tracking
        namedWindow("Track", WINDOW_NORMAL);
        imshow("Track", scene);

        /// Gibt die Koordinaten des Matches im Bild an
        //putText(scene, "(" + intToString(match_centers[i].x) + "," + intToString(match_centers[i].y) + ")", Point(match_centers[i].x - 40, match_centers[i].y - 15), 1, 1, Scalar(255, 0, 0));
    }
}


vector<Point> imageComparetion(Mat object, Mat scene, int match_method, float peek_percent) {

    scene.copyTo(image_display);
    object.copyTo(image_object);

    result_cols = scene.cols - object.cols + 1;
    result_rows = scene.rows - object.rows + 1;
    Mat result(result_cols, result_rows, CV_32FC1);

    /// match scene with template
    matchTemplate(scene, object, result, match_method);

    ///normalize(result, result, 0, 1, NORM_MINMAX, -1, Mat());
    normalize(result, result, 0, 1, NORM_MINMAX, -1, Mat());

    /// For SQDIFF and SQDIFF_NORMED, the best matches are lower values. For all the other methods, the higher the better
    if (match_method == TM_SQDIFF || match_method == TM_SQDIFF_NORMED)
    {
        matchLoc = minLoc;
        threshold(result, result, 0.1, 1, THRESH_BINARY_INV);
    }
    else
    {
        matchLoc = maxLoc;
        threshold(result, result, 0.9, 1, THRESH_TOZERO);
    }

    vector<Point> res;
    maxVal = 1.f;

    Mat input_matrix = image_display; //webcam image into matrix
    Mat match = Mat(input_matrix.size(), input_matrix.type(), Scalar::all(0));

    while (maxVal > peek_percent) {

        minMaxLoc(result, &minVal, &maxVal, &minLoc, &maxLoc, Mat());

        if (maxVal > peek_percent) {

            Rect r1(Point(maxLoc.x - object.cols / 2, maxLoc.y + object.rows / 2), Point(maxLoc.x + object.cols / 2, maxLoc.y - object.rows / 2));
            rectangle(result, Point(maxLoc.x - object.cols / 2, maxLoc.y - object.rows / 2), Point(maxLoc.x + object.cols / 2, maxLoc.y + object.rows / 2), Scalar::all(0), -1);
            res.push_back(maxLoc);

        }

    }

    return res;

}


int main(int argc, char** argv) {


    ///open Cam
    VideoCapture cap(1);
    cap.set(CAP_PROP_FRAME_WIDTH, 1920);
    cap.set(CAP_PROP_FRAME_HEIGHT, 1080);

    ///Check if cam is open
    if (!cap.isOpened()) {
        cout << "\n Bitte Verbindung zur Kamera ueberpruefen! \n";
        return 0;
    }


    ///Read the matches template
    image_template = imread("C:/Users/Ceraxes/Pictures/glaspol.jpg");
    Mat current = imread("C:/Users/Ceraxes/Pictures/glaspol.jpg");


    cap >> image_input;


    ///find location of template in stream
    vector<Point> match_centers = imageComparetion(image_template, image_input, TM_CCOEFF_NORMED, 0.3); //template, picture, matching method, treshold(peak percent)

    /// shows the found template
    drawMatch(image_template, image_input, match_centers);

    waitKey(1);

    ///build window
    namedWindow("IDS", WINDOW_NORMAL);
    Mat detect = image_input; //img_display
    Mat draw = Mat(detect.size(), detect.type(), Scalar::all(0));


    while (true) {

        cap >> detect;

        ///Show image from camera
        imshow("IDS", detect);      

        /// check every found match
        while (i < match_centers.size()) {

            ///Extract the found matches from the picture

            Rect r3(Point(match_centers[i].x, match_centers[i].y), Point(match_centers[i].x + image_template.cols, match_centers[i].y + image_template.rows));

            ///compares the camera imgage with the template
            absdiff(detect(r3), current, pictureTest);

            ///counts the differences
            blackPixel = countNonZero(pictureTest == 150);


            cout << blackPixel << "\n";

            i++;

        }

        i = 0;

        waitKey(1);

    }

    return 0;

}

Я использую камеру IDS ueye, openCV 4 и Visual Studio 2017.

У кого-нибудь есть идеи, почему алгоритм замедляется?

...