一个程序,我们通过输入不同的命令行参数,就可以实现一个可执行文件,多种功能,通过命令行来控制它的行为,例如,我们在控制台的时候,就是遇到最多的,如一个exe程序,加入为test..exe,我们可以设置一些命令行参数,如/t,/q,在我们输入不同的命令行的时候,实现不同的行为,但是一般在控制台见得普遍,在窗口化程序中,是否没有怎么看到,之所以我们没有看到,是因为使用的方式不同,对于窗口化的程序,我们通常根据功能的不同,我们把这些参数都写入了注册表,然后在右键快捷菜单中设置相应的菜单项,当我们选择不同的菜单项目的时候,其实就是使用了通过不同的命令行来达到不同的程序行为,另外,我们还可以在我们编写的mfc程序中,通过参数来控制行为以后,我们不在继续执行,创建窗口等操作,而是直接退出。如此一来,我们就可以通过一个exe文件实现不同的功能,如一个基于对话框的程序,我们通过输入不同的参数以后,可以实现一些功能,但是呢,我们不启动对话框。那么,下面就来说说如何mfc是如何使用命令行的。

在文档类的InitInstance中会看到这样的一句话,前面是一个类,这个类只有一个方法,就是CCommandLineInfo::ParseParam,别的全是数据成员和构造函数,ParseCommandLine函数是CWinapp的一个方法,它以cmdInfo对象为参数,它的作用就是重复的调用ParseParam方法来解析传入程序的命令行,根据标记和参数来填充CCommandLineInfo的数据成员,它是重复调用的,直到将所有的参数解析完毕。然后我们在这段代码的下面,找到一句:

if (!ProcessShellCommand(cmdInfo))
        return FALSE;

这个就是通过参数,执行相应的命令,如打开文件,新建文件等等命令,这些都可以在MSDN的CWinapp类中找到,但是呢,这些都是默认的,MFC内置的命令,如果我们要实现我们自己的命令参数呢,应该如何做呢,那么,我们应该自定义一个类,这个类继承了CCommandLineInfo类,这里顺便说一下如何添加类到MFC到我们的项目中,通过类向导,选择添加MFC类,如下图:

这中添加方式,就可以直接将相应的头文件,源文件关联然后加入项目中,而且类的基本框架页实现了,但是有的类,如我们现在要添加一个继承自CCommandLineInfo类的自定义类,我们发现,没有这个基类,那么应该如何做呢,我们可以选择继承自CObject类,这个类是所有mfc类的基类,它是一个很重要的类,同学们可以到msdn中查阅学习。继续刚才的,我们继承了CObject这个类,但是我们不是要继承CCommandLineInfo类吗,其实这不要紧,看下图:

我们只要将CObject换成我们的CCommandLineInfo类,这样就可以了,大家可以看到,用这种方式添加的类,构造函数,析构函数都有了,所以建议大家用这中方式添加自定义MFC类。在这里,我添加了两个数据成员,分别为TCHAR类型的常量指针,之所以为常量,是为了和我们后面要写的ParseParam相对应。我用这两个变量来保存我们自定义的命令行标记和参数。命令行里面的标记呢,是指如/t,-t,这样的就是标记,在解析的时候,自动将/和-符号移除。加/和-的效果是一样的,关键是标记后面的值。参数,如我们打开一个文件,“C:\Test.txt”,用双引号引起来的,就是参数。在解析的时候,引号也自动去掉。如果我们的参数中必须要有引号,那么在最外面的引号里面通过转义字符来表示如\",这样一来,就可以将双引号包含如命令中。最后,我重写了CCommandLineInfo类唯一的方法ParseParam方法,如下图:

由上面可以看到,bFlag是一个布尔值,如果是TURE,说明这个命令行是一个标记,那么就将它存入F中,否则就是参数,存入P中。最后在调用基类的方法,主要是响应MFC默认的一些命令,当然,这里呢,对于是否调用基类的判断不是很好,大家根据自己的实际情况,来设定。如此一来,我们就可以获取我们定义的命令行了。下面是如何处理我们自定义的命令行

在最初的基础之上,我先处理了自己的自定义的命令行,然后根据需要来看是否调用处理默认的MFC命令。这是在mfc的文档类中,我们充分利用了mfc框架,实现了自定义命令行的实现,那么我们还有一种方式,这种方式和SDK的WinMain函数中处理由WinMain函数传递进来的命令行处理是一样的,如下:

int CALLBACK WinMain(
_In_  HINSTANCE hInstance,
_In_  HINSTANCE hPrevInstance,
_In_  LPSTR lpCmdLine,
_In_  int nCmdShow
);

其中lpCmdLine就是命令行,下面我就在基于对话框的MFC程序中说明一下。

WinMain的这个参数传递进来以后,就把值赋给了app类的m_lpCmdLine数据成员中,那么我们只要解析它就可以了,如下图:

在这里我们在输出窗口中可以看到m_lpCmdLine中的值,就是我调试的时候设置的命令行。然后我通过一个while语句,将字符指针中的字符复制到一个字符数组中,因为字符数组通过索引来查找字符,便于我们解析。但是这个要麻烦一点,因为不会像MFC提供的CCommandLine类一样为我们自动移除引号和/,-标记。这些全部要我们自己来操作。那么,我们默认调试运行的时候,参数是空,我们如何在调试的时候加入参数呢,见下图:

在属性当中,调试,命令参数中,我们就可以输入参数,在运行的时候,就可以传入参数,来帮助我们调试不同命令行下的参数运行情况。那么,第二种方式,就完全和SDK总的WinMain中的参数解析一样的,如此一来,就完全没有使用MFC提供给我们的方法,就是麻烦一点,但是有大的灵活性。

最后,总结一下,通过命令行,控制我们程序启动时的行为,实现一个exe文件,多个功能,如在上面的例子中,我们可以在处理我们自己的命令之后,可以返回,退出,而不继续执行,建立窗口。但是大家要记住处理命令行的地方,那就是在app类的InitInstance方法中,应该在调用基类的CWinApp::InitInstance();方法之前调用,因为基类的这个方法就开始创建实例了,如果再创建实例之后,处理我们自己的命令行就直接返回,会造成内存泄露的情况。

MFC的命令行的更多相关文章

  1. MFC接收命令行参数的三种方法

    方法一: CString sCmdline = ::GetCommandLine(); AfxMessageBox(sCmdline); 将获取到 "C:\test\app.exe -1 - ...

  2. 命令行下的C++程序转换成VC的MFC程序需要注意的问题

    在将命令行下的C++程序转换成MFC窗口程序时一般会提示下面这种错误: fatal error C1010: unexpected end of file while looking for prec ...

  3. <VS>MFC程序显示命令行窗口

    编写MFC程序时,想打印出调试信息,使用cout后,发现程序并没有像想象中那样自动弹出命令行窗口,要输出的信息也没地方去查看.百度后知道要手动调出命令行窗口,才可以看到输出的信息.   百度上介绍了两 ...

  4. MFC命令行及CCommandLineInfo类

    获取命令行的方法: 1.GetCommandLine() 获取输入的所有信息,包括程序所在路径及参数 2.AfxGetApp()->m_lpCmdLine 只包含参数 一般情况下,获取到命令行后 ...

  5. Windows的命令行查看,修改,删除,添加环境变量

    查看当前所有可用的环境变量:输入 set 即可查看. 显示某环境变量: 例如:echo %SystemDrive% 类似linux下面的echo $PATH这种用法. 首先明确一点:所有的在cmd命令 ...

  6. 转 命令行下玩VC

    说明:(1)转载请注明出处:http://www.cnblogs.com/opangle/p/4298155.html (2)以下以VS2013为例,并假设VC安装路径为%VC_INSTALL_PAT ...

  7. 命令行下玩VC

    说明:(1)转载请注明出处:http://www.cnblogs.com/opangle/p/4298155.html (2)以下以VS2013为例,并假设VC安装路径为%VC_INSTALL_PAT ...

  8. 用Visual Studio创建集成了gtest的命令行工程

    gtest代码库中的sample代码 在gtest的代码库中,包含了10个sample的代码,覆盖了gtest的常见用法,sample的代码位于以下文件夹: gtest\samples 由于gtest ...

  9. Windows 编程,程序编译使用的命令行工具。

    Windows 编程,程序编译使用的命令行工具. 1.cl.exe文件是Visual C\C++的编译器,它将程序源代码文件编译为obj文件. 2.rc.exe文件是资源编译器.工程项目中的.rc文件 ...

随机推荐

  1. PHP中简单的图形处理

    PHP中简单的图形处理 计应134凌豪 1.加载GD库 GD库是一个开放的动态创建图像.源代码公开的函数库,可以从官方网站http://www.boutell.com/gd处下载.目前,GD库支持GI ...

  2. NET Core开发-读取配置文件Configuration

    ASP.NET Core开发-读取配置文件Configuration   ASP.NET Core 是如何读取配置文件,今天我们来学习. ASP.NET Core的配置系统已经和之前版本的ASP.NE ...

  3. Ghost win7 系统安装(虚拟机)

    1.将Ghost.iso添加到数据存储iso文件中,启动虚拟机,根据相关提示,文件格式化系统硬盘,完成操作后关机: 2.进入BIOS,设置从CDROM启动系统(否则系统会提示找到引导文件): 3.将系 ...

  4. uva10934 Dropping water balloons

    //好久没做题 一直没状态 然后刷了个水题玩玩 //寒假集训和校赛都做到了类似的题目 然而当时并不会 (其实现在也不会 题意:有k个气球和一个n层高的楼,气球有硬度,在某曾会恰好摔碎,问至少多少次实验 ...

  5. 海康威视研究院ImageNet2016竞赛经验分享

    原文链接:https://zhuanlan.zhihu.com/p/23249000 目录 场景分类 数据增强 数据增强对最后的识别性能和泛化能力都有着非常重要的作用.我们使用下面这些数据增强方法. ...

  6. mit java open course assignment #4

    package come; public class Library { // Add the missing implementation to this class String realLoca ...

  7. ASP.NET repeater添加序号列的方法

    ASP.NET repeater添加序号列的方法 1.<itemtemplate> <tr><td> <%# Container.ItemIndex + 1% ...

  8. python 网页爬虫+保存图片+多线程+网络代理

    今天,又算是浪费了一天了.python爬虫,之前写过简单的版本,那个时候还不懂原理,现在算是收尾吧. 以前对网页爬虫不了解,感觉非常神奇,但是解开这面面纱,似乎里面的原理并不是很难掌握.首先,明白一个 ...

  9. Math.round(11.5)等于()Math.round(-11.5)等于()

    几天前去面试,这道简单的题目居然做错了,看来基础就是慢慢积累的.并不断使用和复习才会成为高手,假设基础不是那么熟练.恐怕在成为高手的路上会困难重重.所以在做项目的间歇时间.偶尔回顾一下最基础的知识.是 ...

  10. Body joints angle using Kinect

    http://stackoverflow.com/questions/12608734/body-joints-angle-using-kinect-checking-time-interval?rq ...