• OpenCV中CommandLineParser命令行输入使用方法介绍


    OpenCV的语义分割代码里面,随处可见的CommandLineParser类。将不同的模型和配置文件,都单独拎出来,用命令行输入进行配置。因此,需要了解基本的使用方法。

    OpenCV中CommandLineParse类主要是命令行解析类。OpenCV中出现此类的主要目:方便用户在命令行使用过程中减少工作量。具体使用方式如下。

    我们将从三个方面介绍。首先是CommandLineParser类的构造函数,说明一下这个类的一些常用成员函数;随后介绍如何按需添加和配置参数和变量;最后直接使用Visual Studio 或者生成的exe文件,来按照命令行的方式,输入参数,并运行得到结果。

    1. CommandLineParser构造类简介

    class CV_EXPORTS CommandLineParser
    {
    public:
     
    	/*
    	* 函数功能:构造函数
    	* 参数:
    	*   [in]     argc        main函数中的第一参数,即运行程序中获得指令的个数
    	*   [in]     argv        main函数中的第二个参数,即运行程序中指令的内容
    	*   [in]     key_map     当启动程序是没有输入任何指令,则使用key_map中默认的指指令。
    	* 备注:
    	*   key_map中的格式:
    	*       "{    s|  123asd       |string parameter}
    	*        {    d|  100          |digit parameter }
    	*        {   @c|  false        |without camera  }
    	*        {    1|  some text    |help            }
    	*        {    2|  333          |another help    }"
    	*参数or指令名称|指令or参数内容 |指令说明
    	*
    	*
    	*  运行程序输入指令的方式如下:(例如程序名称为extest.exe)
    	*  extest.exe -s=123asdd -d=1000 -@c=10
    	*  注意:指令名称前面需要加一个“-”,或“--”。当输入指令后面没有参数,默认为true
    	*       另外,前面加@的指令可以不输入指令名称,直接设置指令内容即可。
    	*       没有输入的指令,则使用key_map中的默认值
    	*/
    	CommandLineParser(int argc, const char* const argv[], const String& keys);
     
     
    	CommandLineParser(const CommandLineParser& parser);
     
     
    	CommandLineParser& operator = (const CommandLineParser& parser);
     
     
    	~CommandLineParser();
     
     
    	String getPathToApplication() const;
     
    	/*
    	* 函数功能:获得指令名称的参数值
    	* 参数:
    	*   [in]     name            指令名称,注意此处不要加"-"
    	*   [in]     space_delete    此参数默认为true,把参数内容中的头尾的空格去掉。
    	*/
    	template <typename T>
    	T get(const String& name, bool space_delete = true) const
    	{
    		T val = T();
    		getByName(name, space_delete, ParamType<T>::type, (void*)&val);
    		return val;
    	}
     
     
    	template <typename T>
    	T get(int index, bool space_delete = true) const
    	{
    		T val = T();
    		getByIndex(index, space_delete, ParamType<T>::type, (void*)&val);
    		return val;
    	}
     
     
    	/*
    	* 函数功能:查看是否有此指令名称,如果没有此指令名称报错;若果有此指令,并且此指令有值,则返回true
    	* 参数:
    	*   [in]     keys            指令名称
    	* 返回值
    	*   含有返回true
    	* 备注:
    	*     此函数本质上是检查两个东西:
    	*     1、此指令是否存在
    	*     2、此指令对应的指令内容存在;
    	*     以上二者都存在,返回true;
    	*     所以,只要在命令行输入此值令,并且指令存在,一定返回ture.(因为如果不指定参数内容,系统会默认true)
    	*     但是,在构造函数key_map中,如果指令参数没有填写。即使key_map中存在此指令,也会返回false。(因为没有参数内容)(另外;前提是命令行没有输入此指令)
    	*/
    	bool has(const String& name) const;
     
    	/*
    	* 函数功能:检查输入的指令是否有有错误,即无法解析
    	* 参数:
    	*   [in]
    	* 返回值:
    	*    没有错误返回true,有错误返回false
    	*/
    	bool check() const;
     
     
    	void about(const String& message);
     
     
    	void printMessage() const;
     
     
    	void printErrors() const;
     
    protected:
    	void getByName(const String& name, bool space_delete, int type, void* dst) const;
    	void getByIndex(int index, bool space_delete, int type, void* dst) const;
     
    	struct Impl;
    	Impl* impl;
    };
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 101
    • 102
    • 103
    • 104
    • 105

    2. CommandLineParser的使用方法

    在keys中,添加需要命令行输入的参数,如下,OpenCV的语义分割模块c++代码中的片段。我们需要添加模型文件:model;输入图像:image;输出结果:result;是否展示image:show。
    单个参数,是按照如下方式定义的:
    “{ arg_name | default number | argument description}”
    {输入参数的名称 m | 默认值 | 参数的描述性文字}.

    const String keys =
            "{help h    || Sample app for loading ENet Torch model. "
                           "The model and class names list can be downloaded here: "
                           "https://www.dropbox.com/sh/dywzk3gyb12hpe5/AAD5YkUa8XgMpHs2gCRgmCVCa }"
            "{model m   |./model-cityscapes.net| path to Torch .net model file (model_best.net) }"
            "{image i   |./car.jpg | path to image file }"
            "{result r  | out_result.pb | path to save output blob (optional, binary format, NCHW order) }"
            "{show s    |true | whether to show all output channels or not}"
            "{o_blob    || output blob's name. If empty, last blob's name in net is used}";
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    要想直接运行,可以将参数的默认值添加进去。如代码所示,我们将model的名称,model-cityscapes.net添加进去了。将image 设置为car.jpg。我们指定了显示结果,show设置为true。

    在下面的代码中,可以直接获取相关参数和变量的值。

    int main(int argc, char **argv)
        CommandLineParser parser(argc, argv, keys);
    
        if (parser.has("help"))
        {
            parser.printMessage();
            return 0;
        }
    
        String modelFile = parser.get<String>("model");
        String imageFile = parser.get<String>("image");
    
        if (!parser.check())
        {
            parser.printErrors();
            return 0;
        }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    3. 实际运行与命令行输入技巧

    有两种方式,可以运行代码。

    3.1 直接Visual Studio运行

    Ctrl+F5 release模型,或者F5,debug模式。
    此时,直接将改变的参数,在 String keys里面设置好。就不用输入命令行。跟日常的写代码,调试一样。将配置的模型与参数,直接修改在CommandLineParser的默认值里面,这样方便调试。

    3.2 命令行输入

    当代码调试好,需要只用使用。此时,需要生成exe文件,然后将不同的image采用命令行的方式,输入给exe,运行并观察结果就行。
    首先,需要生成代码的可执行文件,例如,SemanticSeg.exe。 这个文件在./x64/release/ 下面(如果你是release模型生成的exe)。
    然后,在Windows的cmd命令行输入里面(Win+R快捷键打开。)
    cd到exe文件夹下面。

    SemanticSeg.exe -m=…/path/to/modelfile.net -i=…/path/to/image.jpg -s=true

    回车,就可以将数据输入到exe里面,并执行。
    记住,每个参数,在命令行里面,用等于=赋值。例如:-m=model-cityscapes.net , --image=car.jpg。而不是,python里面的, -m ./path/to/model.net,中间用空格来输入。

  • 相关阅读:
    力矩传感器模拟量与ADC采集输出数字量之间的关系
    [m0leCon beginner 2022] 部分
    python一键过杀软
    Spring AOP(二)自定义注解
    springboot+jsp学生成绩查询考务系统
    apollo通过域名访问-Portal挂载到nginx/slb后如何设置相对路径?
    Sqoop的介绍和安装
    制作linux下grup启动背景图片
    IEC101规约总结
    计算机网络期末复习-Part2
  • 原文地址:https://blog.csdn.net/qq_32998593/article/details/125892768