Невозможно использовать анализатор командной строки в opencv

#c #opencv

#c #opencv

Вопрос:

У меня есть следующий код:

 int main(int argc, char** argv)
{
    cv::CommandLineParser parser(argc, argv,
            "{eyes||}{nose||}{mouth||}{help h||}");
    if (parser.has("help"))
    {
        help();
        return 0;
    }
    input_image_path = parser.get<string>(0);
    face_cascade_path = parser.get<string>(1);
    eye_cascade_path = parser.has("eyes") ? parser.get<string>("eyes") : "";
    nose_cascade_path = parser.has("nose") ? parser.get<string>("nose") : "";
    mouth_cascade_path = parser.has("mouth") ? parser.get<string>("mouth") : "";
    if (input_image_path.empty() || face_cascade_path.empty())
    {
        cout << "IMAGE or FACE_CASCADE are not specifiedn";
        return 1;
    }
    // Load image and cascade classifier files
    Mat image;
    image = imread(input_image_path);
  

Когда я запускаю код следующим образом: ./code help

Или как,

 ./code eyes: /home/Users/Matt/rob.jpg
  

Это всегда выдает мне ошибку: IMAGE or FACE_CASCADE are not specified . Я что-то здесь упускаю? Я перешел по этой ссылке http://docs.opencv.org/trunk/d0/d2e/classcv_1_1CommandLineParser.html и ввожу команду, указанную там, но она по-прежнему не принимает аргумент.

Ответ №1:

Есть несколько ошибок:

  1. вы не указываете позиционные аргументы для input_image_path и face_cascade_path в parser ключах.
  2. чтобы использовать непозиционные аргументы, вам необходимо использовать -arg= , например: -eyes=/path/to/eyes.xml

Вы можете проверить приведенный ниже код с правильными ключами и примерами вызовов. Для полноты я указал изображение как обязательное ( <none> значение по умолчанию) и значение по умолчанию для каскадного пути лица.

Этот код работает, как и ожидалось, с OpenCV 3.1. Предыдущие версии не поддерживаются <none> .

Вы можете вызвать эту программу как:

 ./foo -help  // -> show help
./foo /path/to/image // -> use dafault face cascade
./foo /path/to/image /path/to/face_cascade
./foo /path/to/image /path/to/face_cascade -eyes=/path/to/eyes_cascade
  

и так далее.

Код:

 #include <opencv2opencv.hpp>

int main(int argc, char** argv)
{
    cv::String keys =
        "{@image |<none>           | input image path}"         // input image is the first argument (positional)
        "{@face  |/path/to/file.xml| face cascade path}"        // optional, face cascade is the second argument (positional)
        "{eyes   |                 | eye cascade path}"         // optional, default value ""
        "{nose   |      | nose cascade path}"       // optional, default value ""
        "{mouth  |      | mouth cascade path}"      // optional, default value ""
        "{help   |      | show help message}";      // optional, show help optional


    cv::CommandLineParser parser(argc, argv, keys);
    if (parser.has("help")) {
        parser.printMessage();
        return 0;
    }

    cv::String input_image_path = parser.get<cv::String>(0); // read @image (mandatory, error if not present)
    cv::String face_cascade_path = parser.get<cv::String>(1); // read @face (use default value if not in cmd)

    bool hasEyeCascade = parser.has("eyes");
    bool hasNoseCascade = parser.has("nose");
    bool hasMouthCascade = parser.has("mouth");
    cv::String eye_cascade_path = parser.get<cv::String>("eyes"); 
    cv::String nose_cascade_path = parser.get<cv::String>("nose"); 
    cv::String mouth_cascade_path = parser.get<cv::String>("mouth");


    if (!parser.check()) {
        parser.printErrors();
        return -1;
    }

    // No errors!

    // image path always present
    //cv::Mat img = cv::imread(input_image_path);

    // face cascaed path always present (eventually the default value)
    // load face cascade

    // You need to check optional arguments
    if (hasEyeCascade) {
        // load eye cascade
    }
    // You need to check optional arguments
    if (hasNoseCascade) {
        // load nose cascade
    }
    // You need to check optional arguments
    if (hasMouthCascade) {
        // load mouth cascade
    }

    // Do your stuff

    return 0;
}