当前位置: 首页 > 编程日记 > 正文

C++ 中隐藏DOS调用的命令行窗口

转自:http://hi.baidu.com/jackyho2000/blog/item/b5c5fabdd3b4db0019d81fbb.html

我演示了一下在MFC程序中怎么应用DOS的dir的命令,可是我们遇到了需要解决的问题,首先就是文件dir.txt的残留问题,其实这个问题很简单,我们也可以用dos的del命令在操作后将dir.txt文件删除,这样的结果就是程序会两次弹出窗口,这样更加让人无法接受了,现在我们的问题是,有没有办法隐藏弹出窗口?答案是有的,这点我在网上找了很久,都没有找到解答,最后自己摸索出了一些方法,不知道还有没有更好的方法,因为这些方法都有些缺点,比较恼火。

首先,我们可以用第二参数为SW_HIDE调用WinExec()这个windows的API,这时候又有个问题了,WinExec()是调用程序的,而DIR程序文件在哪里?呵呵,其实这点在有很多DOS使用经验的人都知道,DOS命令在以前就分两种,一种叫内部命令,一种叫外部命令。其中比较常用的比如dir,del都属于内部命令,特点是直接加载进内存。而外部命令是可以在目录中找到具体的文件的,当时就会常常遇到PATH设定不对导致的外部命令调用错误,而需要找到目录去调用的情况。既然加载在内存里面,我们到哪里去找命令文件?答案我不知道,不过有个变通的方法。因为在windows中,DOS的实际调用都是用cmd程序,那么我们就用它来调用,具体方法是以/C为参数调用。比如我们要调用dir命令,那么具体方法如下:

WinExec("cmd /C dir");

理由可以参考help cmd。当然我们还是有以前那样的问题,那就是dir后面跟具体目录做参数的时候需要加引号,那么我们调用目录的时候一般可以用下面的形式:

WinExec("cmd /c dir /"xxxxx/");

这种方法在直接调用的时候很好用,比如删除文件的时候,直接一个WinExec("cmd /c del dir.txt");就可以了,但是也是有个问题,这是个太老的API了,所以根本没有Unicode的版本,苦闷的Unicode版本程序因此无法较好的使用,在以CString为字符串调用的时候似乎只有两种方法,一种是以ANSI方式编译,一种就是通过Unicode到ANSI的转换了,这样的转换很可能还会丢失中文信息。因此,个人推荐只在直接调用DOS命令的时候使用WinExec,而且也推荐直接调用的时候使用,因为WinExec只需要两个参数,很容易调用。但是要在Unicode程序中以CString为参数调用怎么办?当然,用MSDN中推荐的CreateProcess不会有任何问题,问题是,太复杂了。。。。。个人推荐另一个方案,ShellExecute。虽然比WinExec复杂一点,但是还可以接受。函数原型如下:

HINSTANCE ShellExecute(

HWND hwnd,

LPCTSTR lpOperation,

LPCTSTR lpFile,

LPCTSTR lpParameters,

LPCTSTR lpDirectory,

INT nShowCmd

);

这里,hwnd直接用窗口的句柄就可以了,lpOperation可以省略,默认为open,lpFile我们调用cmd,lpParameters我们加入参数,注意的是cmd要多个/C参数,目录可以为空,nShowCmd为SW_HIDE以达到我们的目的,同上面的情况,调用ShellExecute的时候为以下形式:

ShellExecute(m_hWnd, NULL, _T(cmd), _T("/C dir /"xxxxxx/"");

比如在上一节的例子中,我们调用ShellExecute的方法就是下面这样:

CString dir = _T("/C dir /"") + m_directory + _T("/" >dir.txt");

ShellExecute(m_hWnd, NULL, _T("cmd"), dir, NULL, SW_HIDE);

然后,改变后你会发现程序在第一次调用的时候不会有任何反应,一定要第二次点击按钮才能生效,原因可能会令人很困惑,有多线程编程经验的人可能会反应过来,因为ShellExecute的调用实际上是新开了一个线程,那么所有关于多线程编程让人郁闷苦恼烦躁的问题都完全适用。这里,问题在于,ShellExecute新开线程后直接返回了,不等dir调用完成,那么下面接着的打开文件根本就找不到文件,我给出一种解决方案,在打开文件的时候检测一下,然后用Sleep休息200毫秒,再检测,如此可以达到需要的要求:

while(!infile.is_open())

{

static int i = 0;

::Sleep(200);

infile.open("dir.txt");

++i;

if(i > 50)

{

MessageBox(_T("Error to create and open the file"));

exit(EXIT_FAILURE);

}

}

经过完善,上节中ReadFromDir函数完整结果如下:

std::string CTestDialogDlg::ReadFromDir()

{

UpdateData();

CString dir = _T("/C dir /"") + m_directory + _T("/" >dir.txt");

// _wsystem(dir);

std::string strFile,strTemp;

ShellExecute(m_hWnd, NULL, _T("cmd"), dir, NULL, SW_HIDE);

// WinExec(dir, SW_HIDE);

std::ifstream infile;

while(!infile.is_open())

{

static int i = 0;

::Sleep(200);

infile.open("dir.txt");

++i;

if(i > 50)

{

MessageBox(_T("Error to create and open the file"));

exit(EXIT_FAILURE);

}

}

while(std::getline(infile, strTemp))

{

strFile += strTemp + "/n";

}

infile.close();

WinExec("del dir.txt", SW_HIDE);

// _wsystem("del dir.txt");

return strFile;

}

经过如上改变,再使用程序,没有看到源代码的人,谁还知道你是用了DOS的DIR命令实现的呢?

这一节的主要内容是给广大因为使用了DOS命令而导致程序运行效果不佳老弹出窗口的同志们信心,大胆的调用DOS命令吧,没有人知道的,只要能简单的完成任务,我们不择手段,呵呵。

///

转自:http://hi.baidu.com/notepad519/blog/item/0f126643545eae1673f05dc7.html

去除控件台程序中的窗口显示

总的来说都来改变程序的入口点来达到目的:

1.

#pragma comment(linker, "/subsystem:windows /entry:mainCRTStartup")
#include <iostream>
using namespace std;
int main(void)

{
   cout<<"河北经贸大学"<<endl;
return 0;

}

在Cdm下 文件名.exe>>新的文件名.txt(格式后缀可变) 可以进行查看输入内容。

2.

#pragma comment( linker, "/subsystem:windows" )
#include   <windows.h>
int APIENTRY WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR     lpCmdLine,
int       nCmdShow)
{
MessageBox(NULL,"显示内容","标题",0);
     return 0;
}


后记:一开始用的是AfxMessageBox 出现以后错误
'AfxMessageBox' : undeclared identifier
原因是:因为AfxMesageBox(   )函数是
MFC类库提供的函数,而Console程序又没有提供支持   MFC,
所以就不应该使用这个函数了。要实现用API函数
MessageBox(   )来实现。
注意需要在添加   #include   <windows.h>

3、subsystem和可执行文件的启动
LINK的时候需要指定/subsystem,这个链接选项告诉Windows如何运行可执行文件。
控制台程序是/subsystem:"console"
其它程序一般都是/subsystem:"windows "

将 subsystem 选成"console"后,Windows在进入可执行文件的代码前(如mainCRTStartup),就会产生一个控制台窗口。
如果选择"windows",操作系统就不产生console窗口,该类型应用程序的窗口由用户自己创建。

可执行文件都有一个Entry Point,LINK时可以用/entry指定。缺省情况下,如果subsystem是“console”,Entry Point是 mainCRTStartup(ANSI)或wmainCRTStartuup(UNICODE),即:
/subsystem:"console" /entry:"mainCRTStartup" (ANSI)
/subsystem:"console" /entry:"wmainCRTStartuup" (UNICODE)
mainCRTStartup 或 wmainCRTStartuup 会调用main或wmain。
值得一提的是,在进入应用程序的Entry Point前,Windows的装载器已经做过C变量的初始化,有初值的全局变量拥有了它们的初值,没有初值的变量被设为0。

如果subsystem是“windows”,Entry Point是WinMain(ANSI)或wWinMain(UINCODE),即:
/subsystem:"windows" /entry:"WinMainCRTStartup" (ANSI)
/sbusystem:"windows" /entry:"wWinMainCRTStartup" (UINCODE)
WinMainCRTStartup 或 wWinMainCRTStartup 会调用 WinMain 或 wWinMain。

如果使用MFC框架,WinMain也会被埋藏在MFC库中(APPMODUL.CPP):
extern "C" int WINAPI
_tWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
LPTSTR lpCmdLine, int nCmdShow)
{
// call shared/exported WinMain
return AfxWinMain(hInstance, hPrevInstance, lpCmdLine, nCmdShow);
}
"_t"是一个宏,对于ANSI版本,"_tWinMain"就是"WinMain";对于UINCODE版本,"_tWinMain"就是"wWinMain"。

全局C++对象的构造函数是在什么地方调用的?答案是在进入应用程序的Entry Point后,在调用main函数前的初始化操作中。所以MFC的theApp的构造函数是在_tWinMain之前调用的。


4、不显示Console窗口的Console程序
在默认情况下/subsystem 和/entry开关是匹配的,也就是:
"console"对应"mainCRTStartup"或者"wmainCRTStartup"
"windows"对应"WinMain"或者"wWinMain"
我们可以通过手动修改的方法使他们不匹配。例如:

#include "windows.h"
#pragma comment( linker, "/subsystem:/"windows/" /entry:/"mainCRTStartup/"" ) // 设置入口地址
void main(void)
{
MessageBox(NULL, "hello", "Notice", MB_OK);
}

这个Console程序就不会显示Console窗口。如果选/MLd的话,这个程序只需要链接LIBCD.LIB user32.lib kernel32.lib

相关文章:

Citrix Avalon安装实验手册之一----Avalon概述及实验环境准备

“Avalon”&#xff08;阿瓦隆&#xff09;是思杰下一代桌面/应用交付产品的项目名称&#xff0c;其核心目标是把现有Windows应用和桌面转换成云服务。 其中你最熟悉的XenApp和XenDesktop就是Avalon项目的核心所在。Avalon这个全新解决方案将XenApp、XenDesktop、CloudGateway、…

图片像素、英寸、厘米之间的单位换算

转自&#xff1a;http://hi.baidu.com/cjg501/blog/item/f040fc0898d5379f0b7b8244.html 今天朋友用photoshop处理图片时要把图片保存指定的大小&#xff0c;但她只对厘米要形像感&#xff0c;可是在软件里保存的图片没有这个单位&#xff0c;只能保存的单位为像素&#xff1b;…

创客集结号_你知道单机片和Arduino之间的区别吗

Arduino 是一款便捷灵活、方便上手的开源电子原型平台&#xff0c;包含硬件和软件都是开源的。 开源硬件指与自由及开放原始码软件相同方式设计的计算机和电子硬件。开源硬件开始考虑对软件以外的领域开源&#xff0c;是开源文化的一部分。这个词主要是用来反映自由释放详细信息…

痛!“做C#半年,挣的不如做AI 1个月?”看到第二句泪目……

前两天在网上发现一个热门话题&#xff1a;“做开发一年&#xff0c;在北京月薪不到1万&#xff0c;有点迷茫。” 其中&#xff0c;这个回答我永远忘不了&#xff1a;来源&#xff1a;库库的派派知乎回答&#xff0c;已取得授权在这短短的一条信息里&#xff0c;小编佩服不仅…

刷新记录,算法开源!字节跳动获人体姿态估计竞赛双冠 | CVPR 2019

整理 | Jane出品 | AI科技大本营&#xff08;id&#xff1a;rgznai100&#xff09;【导读】6 月 16--20 日&#xff0c;计算机视觉与模式识别领域顶会 CVPR 2019 在美国长滩举行。每年的 CVPR 盛会除了精彩的论文分享、Workshop 与 Tutorial&#xff0c;还会举办多场涵盖计算机…

java 赋值,算术,一元操作符(翻译自Java Tutorials)

原文出自 http://www.cnblogs.com/ggjucheng/archive/2012/12/15/2819621.html 英文出自 http://docs.oracle.com/javase/tutorial/java/nutsandbolts/op1.html 简单赋值操作符 见到的最常用的操作符之一就是简单赋值操作符"".它把值从操作符的右边赋予到左边&#x…

初识Kubernetes(K8s):理论基础

Kubernetes是什么&#xff1f;Kubernetes&#xff0c;简称K8s&#xff0c;是用8代替8个字符“ubernete”而成的缩写。Kubernetes是Google开源的一个容器编排引擎&#xff0c;同时也是一个开源的容器集群管理系统&#xff0c;可以实现容器应用的自动化部署、自动扩缩容、监控和维…

Sobel算子及cvSobel

转自&#xff1a;http://blog.sina.com.cn/s/blog_4bdbec750100mufo.html 由于项目里要用到边缘检测&#xff0c;所以今天研究了一下最简单的梯度的方法。 首先&#xff0c;我们来开一下计算机是如何检测边缘的。以灰度图像为例&#xff0c;它的理论基础是这样的&#xff0c;如…

python全栈开发笔记---------函数

一 数学定义的函数与python中的函数 初中数学函数定义&#xff1a;一般的&#xff0c;在一个变化过程中&#xff0c;如果有两个变量x和y&#xff0c;并且对于x的每一个确定的值&#xff0c;y都有唯一确定的值与其对应&#xff0c;那么我们就把x称为自变量&#xff0c;把y称为因…

OpenCV中的内存泄露问题(cvLoadImage,cvCloneImage)

转自&#xff1a;http://apps.hi.baidu.com/share/detail/30893646 在做项目的过程中&#xff0c;使用OpenCV经常会出现一些内存泄露问题&#xff0c;自己编写的程序出现问题还情有可原&#xff0c;但若是库函数调用和使用时出现&#xff0c;却很令我恼火。花了好长时间和实践的…

41款实用工具,数据获取、清洗、建模、可视化都有了

诸如结构式访谈、非结构式访谈、开放式问卷调查、封闭式问卷调查、记录评论和观察等技术统称为事实调查方法。这种事实调查方法和其他数据获取方法可以采取自动化&#xff0c;而不必使用人工方法。使用具有专用软件的物理设备&#xff08;如终端、传感器和扫描仪等&#xff09;…

OpenCV中的内存泄漏检测

转自&#xff1a;http://chaishushan.blog.163.com/blog/static/130192897200911685559809/ 内存泄漏时程序开发中经常遇到的问题. 而且出现内存泄漏很难检测,但是其导致的结果却是灾难性的. 这里讲一下opencv中内存泄漏检测的一些技巧.OpenCV中关于内存管理主要涉及到以下3个函…

一文全面了解基于内容的推荐算法

作者丨gongyouliu来源 | 转载自大数据与人工智能&#xff08;ID:ai-big-data&#xff09;这篇文章我们主要关注的是基于内容的推荐算法&#xff0c;它也是非常通用的一类推荐算法&#xff0c;在工业界有大量的应用案例。本文会从什么是基于内容的推荐算法、算法基本原理、应用场…

[Nginx优化]分享nginx配置文件及优化说明

1、系统及内核方面 根据服务器用途&#xff0c;建议系统最小化安装或针对web服务器进行系统内核重新编译&#xff1b;在内核参数的一些优化&#xff0c;如下&#xff1a; # Add net.ipv4.tcp_max_syn_backlog 65536 #表示SYN队列的长度 net.core.netdev_max_backlog 3…

laravel项目composer安装

1.下载 Composer &#xff08;https://pkg.phpcomposer.com/#how-to-install-composer&#xff09; 安装前请务必确保已经正确安装了 PHP。打开命令行窗口并执行 php -v 查看是否正确输出版本号。 打开命令行并依次执行下列命令安装最新版本的 Composer&#xff1a; 复制php -r…

淘宝装修:第一日 —— 图片轮播

先添加一个自定义内容区&#xff0c;进入源码编辑&#xff0c;如下图所示&#xff1a; 添加源码如下&#xff1a; <TABLE border0 cellSpacing0 cellPadding0 width773 height220> <TBODY> <TR> <TD width773> <P> <MARQUEE height220 behavi…

强化学习大规模应用还远吗?Youtube推荐已强势上线

来源 | 转载自深度传送门导读&#xff1a;本文将介绍在深度学习的强力驱动下&#xff0c;给推荐系统工业界所带来的最前沿的变化。本文主要根据几大顶会2019的最新论文&#xff0c;总结一下深度强化学习给推荐系统以及CTR预估工业界带来的最新进展。 凡是Google出品&#xff0c…

layui select 与 vue 的结合使用

2019独角兽企业重金招聘Python工程师标准>>> 1. 创建一个select元素 <form class"layui-form layui-form-pane all-account-filter-form"><div class"layui-form-item"><div class"layui-inline"><label class&…

OpenCV 2.2.0 CvvImage的使用

转自&#xff1a;http://blog.csdn.net/raocong2010/archive/2011/01/17/6146158.aspx# 前几日&#xff0c;OpenCV 2.2.0版本出现了...但是...以前版本的CvvImage类不见了...为了能够继续使用这个类&#xff0c;下面把这个类的源代码贴出来&#xff0c;使用的时候将该代码加入到…

c/c++标准预定义宏

转自&#xff1a;http://www.eefocus.com/andysun001/blog/10-06/192018_008b3.html 一、标准预定义宏The standard predefined macros are specified by the relevant language standards, so they are available with all compilers that implement those standards. Older c…

阿里AI攻克心血管识别技术,冠脉中心线提取论文入选国际医学影像会议

阿里在医疗AI领域取得新进展&#xff0c;继创下肺结节检测、肝结节诊断技术的重大突破后&#xff0c;又攻克了难度系数更高的心血管识别技术。 近日&#xff0c;阿里达摩院机器智能实验室有关冠状动脉中心线提取的论文已被国际顶级医学影像会议MICCAI 2019提前接收。 阿里AI论…

自由程序员在国外

可靠的做法是&#xff0c;在一些像oDesk这样的网站上找一些临时开发任务&#xff0c;在Linked In网站上提交一份个人简历。这样将有助于你在出行后尽早的找到可干的项目&#xff0c;而不必到时大减价来抢其他程序员的活儿(或消减自己的预算)。 从来不缺乏你可以捐赠代码的开源项…

关于spring aop Advisor排序问题

关于spring aop Advisor排序问题 当我们使用多个Advisor的时候有时候需要排序&#xff0c;这时候可以用注解org.springframework.core.annotation.Order或者实现org.springframework.core.Ordered接口。 示例代码&#xff1a; import org.aspectj.lang.ProceedingJoinPoint; im…

NLP重大突破?一文读懂XLNet“屠榜”背后的原理

作者 | 李理 原文链接&#xff1a;https://fancyerii.github.io/2019/06/30/xlnet-theory/ 本文介绍XLNet的基本原理&#xff0c;读者阅读前需要了解BERT等相关模型&#xff0c;不熟悉的读者建议学习BERT课程。 语言模型和BERT各自的优缺点 在论文里作者使用了一些术语&#…

CSS3支持IE6, 7, and 8的边框属性

我们都知道&#xff0c;IE 6,7不支持新增加的CSS3属性&#xff0c;甚至与IE8是CSS3还没有完全准备好。你知道吗&#xff0c;今天给大家分享一个脚本工具&#xff0c;可以帮助您启用CSS3的支持IE浏览器&#xff08;IE6&#xff09;与新的CSS3属性&#xff0c;包括&#xff1a;bo…

解决:VS 2005/2008 中 fstream 不能处理带有中文路径的问题

转自&#xff1a;http://blog.csdn.net/code_robot/archive/2010/06/23/5688867.aspx 有时候用ifstream或ofstream打开带有中文路径的文件会失败。 解决办法&#xff1a;1、使用C语言的函数设置为中文运行环境setlocale(LC_ALL,"Chinese-simplified"); 2、使用STL函…

NLP文本标注工具与平台(数据标注公司)

最近在做NLP相关项目&#xff0c;包括句法分析、情感分析等&#xff0c;有大量数据需要标注。我评估了几个文本标注工具&#xff0c;也接触了几家数据标注公司和平台&#xff0c;总结如下&#xff0c;供各位参考。 文本标注平台&#xff08;标注外包公司&#xff09; 数据标注公…

一文读懂基于神经网络的图片风格转移

作者 | moliam转载自 CSDN 博客前言将A图片的风格转移到B图片上&#xff0c;指的是将A图片的抽象艺术风格&#xff08;如线条、色彩等等&#xff09;和B图片的内容框架合成为一幅图。自然地&#xff0c;A图片称为风格图&#xff0c;而B图片就称为内容图。就像这样&#xff1a;左…

【物联网中间件平台-01】真正面向物联网的组态软件 YFIOs和YFHMI的前生今世

1前言 从2001年进入工控领域以来&#xff0c;前后7年多的时间开发了诸如二型计量监控系统、焦炉四大机车自动化系统、烧结配水监控系统、隧道广告影像系统、通用组态软件、嵌入式系统组态软件&#xff08;基于WINCE系统&#xff09;、LED视频影像系统和ICU病室输液管理等系统。…

OpenCV常遇问题解决方法汇总

1、cvLoad的使用和释放&#xff1a; CvMat *mat (CvMat*)cvLoad("a.xml"); cvRelease((void**)&mat); 2、cvCreateMatHeader的使用和释放&#xff1a; CvMat *mat cvCreateMatHeader(4, 2, CV_64FC1); cvReleaseMatHeader(&mat); 在OpenCV2.1及OpenCV2.2中…