单核cpu为每个进程分配时间片,按照某种进程调度算法,来回切换进程,使得看起来像几个程序在同时运行。进程中由线程执行实际的代码,每个线程都有属于自己的专属堆栈
Windows下有CUI(Console User Interface) 和 GUI(Graphical User Interface)两大类应用程序
针对不同的应用程序,需要设计不同入口函数( _tWinMain, _tmain,与处理何种字符串有关)
需要注意的是,在执行入口函数之前,会先执行C/C++运行库启动函数
tip: 以main函数为例, main函数的实际写法如下
int main(int argc, char *argv[])
可以看到main函数的参数表有两个已经定义好的参数,仔细思考,如果在程序一开始就执行main函数中的代码,那么参数表中的参数由谁传递呢,由此推测主函数在运行前,一定有其他的工作,所以存在C/C++运行库启动函数的存在
以下介绍C/C++运行库启动函数所做的工作:
1.获取指向新进程的完整命令行的指针
2.获取指向新进程的环境变量的一个指针
3.初始化C/C++运行库的全局变量。如果包含了stdlib.h, 我们写的代码就可以访问这些变量(包含了argc, argv)
4.初始化C运行库内存分配函数(malloc 和 calloc)和其他底层I/O例程使用的heap
5.调用所有全局和静态C++类对象的构造函数
入口函数介绍:
tWinMain(_UNICODE)
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow);
hInstance
(实例句柄):这是当前应用程序的实例句柄,它是一个指向当前应用程序的实例的标识符。在Windows中,每个运行的应用程序都有自己的实例句柄。(ImageBase的值)hPrevInstance
(先前实例句柄):这个参数在较早的Windows版本中有意义,但在现代的Windows版本中通常被忽略,因为它总是被设置为NULL。lpCmdLine
(命令行参数):这是一个指向包含命令行参数的字符串的指针。你可以使用这些参数来向应用程序传递额外的信息,例如启动参数。(从终端输入, 作用与argv[]类似)nCmdShow
(显示标志):这个参数指定了应用程序窗口的初始显示状态。它可以是以下常量之一:SW_SHOWNORMAL
:显示窗口并将其激活(通常用于正常启动窗口应用程序)。SW_SHOWMAXIMIZED
:显示窗口并将其最大化。SW_SHOWMINIMIZED
:显示窗口并将其最小化。- 等等...
tMain(_UNICODE)
int _tmain(int argc, TCHAR* argv[], TCHAR* env[])
//tip: 在Visual Studio向导生成应用程序时,没有定义 env[], 需要显示定义, 该参数指向环境变量及其值
int argc
:这是一个整数,表示命令行参数的数量。它指示在命令行上传递了多少个参数,包括程序的名称本身。_TCHAR* argv[]
:这是一个指向指针数组的指针,用于表示命令行参数的字符串。每个指针指向一个表示命令行参数的字符串。根据编译时的设置,_TCHAR
可以是char
或wchar_t
,以支持不同字符集。
_tmain
具有与标准的 main
函数相同的功能,但能够根据需要处理不同字符集的字符。这在跨平台开发或需要多语言支持的应用程序中非常有用。根据 _TCHAR
的定义,_tmain
可以自动适应不同字符集的命令行参数。