控制台和GUI
windows有原生的gui,所以系统默认提供了控制台应用入口和应用入口.linux则不一样,x系统是由软件实现胡,所以没有默认gui,需要使用三方库才能开启gui
瘟到死
Windows操作系统在装载应用程序并且做完初始化工作后,就转到程序的入口点开始执行你编写的程序。
程序的默认入口点实际上是由连接程序设置的,不同的连接器选择的入口函数也大都不同。
在VC++ 6.0下,连接器对控制台程序所设置的入口函数是 mainCRTStartup,也就是说Windows操作系统在装载完程序并且初始化完成后,就进入入口函数mainCRTStartup ,然后由它调用你自己编写的 main 函数,开始执行具体的代码;
对于图形用户界面(GUI)程序设置的入口函数是 WinMainCRTStartup,和上面一样,WinMainCRTStartup再调用你写的WinMain 函数执行具体功能。
设置哪个入口点可以由连接器的“/subsystem:”参数确定的,它告诉操作系统如何运行编译连接所生成的.exe可执行文件。
四种方式:“CONSOLE | WINDOWS | NATIVE | POSIX”如果这个选项参数的值为“WINDOWS”,则表示该应用程序运行时不需要控制台。
CONSOLE
win32 字符模式应用程序,此种类型的应用程序在运行的时候会产生一个类似DOS 窗口的控制台窗口,如果在应用程序的主函数为main()或者wmain()时,在默认情况下 该应用程序就是一个控制台应用程序。
WINDOWS
该类型的应用程序不产生console窗口,该类型的应用程序的窗口由用户自己创建,简而言之 就是一个标准的Win32 application,其入口地址为WinMain()函数或者wWinMain()函数的地址, 如果你在应用程序中定义的主函数为WinMain或者wWinMain,在默认情况下该应用程序就是一个 Win32 Application !
内嵌式控制台
顾名思义,我们主动在自己写的GUI程序中,创建一个控制台。在Windows 的API,AllocConsole用来直接为一个进程创建一个控制台。注意,一个进程只能有一个控制台
|
外挂式控制台
这一次我们使用另一个函数:“AttachConsole”:attach的意思很明显:“贴上,依附上,缠上,赖上……:( ”,而它的参数也很直白: 进程ID。 这样,一个GUI程序,完全可以“缠上”另一个进程的控制台(假设它有的话)。如果是要取“父进程”的ID,就方便多了——事实上是不用取,只要填-1就可以了。
基本上, 电脑用户通过操作系统运行一个程序,比如画笔,比如浏览器,比如Word,都是以一个叫“Explorer.exe”的子进程身份启动的。而我们在IDE里调试程序,则程序会以调试器的子进程运行……,可见子进程其实是相当常见的。现在,我们事先写一个控制台的程序,假设称为P程序,以后当S程序(通常是一个GUI程序)需要附加的控制台来输入输出时(效果像方法.1),我们就用P程序来启动S程序,S程序中则通过“AttachConsole(-1)”来“挂”到其父程序(也就是P)的控制台。完成调试之后,就把P程序丢一边,以普通方式运行S程序,则AttachConsole(-1)失败,那些用于调试的cout/cin自然失效。
|
带控制台的父进程
GUI程序默认不带控制台,所以我们现在写一个控制台程序,用它来调用要调试的GUI程序。这本来是一件再简单不过的事了。只要用C语言的system程序就可以了,并且是跨平台的——问题是微软大叔总爱干些半拉子的事。Windows从DOS起家,都过去多少年了,它对控制台支持还是怪怪的,所以system函数在它身上,居然不支持带空格的路径,我们只好找CreateProcess来出气。
int main(int argc, char** argv) |
libc扫盲
ANSI C
ANSI C 函数库是基本的 C 语言函数库,包含了 C 语言最基本的库函数。这个库可以根据头文件划分为 15 个部分,其中包括:
<ctype.h>
:包含用来测试某个特征字符的函数的函数原型,以及用来转换大小写字母的函数原型;<errno.h>
:定义用来报告错误条件的宏;<float.h>
:包含系统的浮点数大小限制;<math.h>
:包含数学库函数的函数原型;<stddef.h>
:包含执行某些计算 C 所用的常见的函数定义;<stdio.h>
:包含标准输入输出库函数的函数原型,以及他们所用的信息;<stdlib.h>
:包含数字转换到文本,以及文本转换到数字的函数原型,还有内存分配、随机数字以及其他实用函数的函数原型;<string.h>
:包含字符串处理函数的函数原型;<time.h>
:包含时间和日期操作的函数原型和类型;<stdarg.h>
:包含函数原型和宏,用于处理未知数值和类型的函数的参数列表;<signal.h>
:包含函数原型和宏,用于处理程序执行期间可能出现的各种条件;<setjmp.h>
:包含可以绕过一般函数调用并返回序列的函数的原型,即非局部跳转;<locale.h>
:包含函数原型和其他信息,使程序可以针对所运行的地区进行修改。地区的表示方法可以使计算机系统处理不同的数据表达约定,如全世界的日期、时间、美元数和大数字;<assert.h>
:包含宏和信息,用于进行诊断,帮助程序调试。
GNU C
glibc是linux下面c标准库的实现,即GNU C Library。GNU C 函数库是一种类似于第三方插件的东西。
由于 Linux 是用 C 语言写的,所以 Linux 的一些操作是用 C 语言实现的,因此,GUN 组织开发了一个 C 语言的库,以便让我们更好的利用 C 语言开发基于 Linux 操作系统的程序。
glibc本身是GNU旗下的C标准库,后来逐渐成为了Linux的标准c库,而Linux下原来的标准c库Linux libc逐渐不再被维护。
Linux下面的标准c库不仅有这一个,如uclibc、klibc,以及上面被提到的Linux libc,但是glibc无疑是用得最多的。glibc在/lib目录下的.so文件为libc.so.6。
libc
libc 是 Linux 下的 ANSI C 函数库;glibc 是 Linux 下的 GUN C 函数库。
libc 实际上是一个泛指,凡是符合实现了 C 标准规定的内容,都是一种 libc 。
- glibc 是 GNU 组织对 libc 的一种实现。它是 unix/linux 的根基之一。
- 微软也有自己的 libc 实现,叫 msvcrt 。
- 嵌入式行业里还常用 uClibc ,是一个迷你版的 libc 。
libc, glibc在一个层次,都是C的标准实现库,是操作系统级别的基石之一。
glib
glib 和 glibc 基本上没有太大联系,可能唯一的共同点就是,其都是 C 编程需要调用的库而已。
glib是用C写的一些utilities,即C的工具库,和libc/glibc没有关系。
glib 可以在多个平台下使用,比如 Linux、Unix、Windows 等。glib 为许多标准的、常用的 C 语言结构提供了相应的替代物。
/www/wwwroot/blog/source/_posts/激光打标glib是GTK+的基础库,它由基础类型、对核心应用的支持、实用功能、数据类型和对象系统五个部分组成,可以在[http://www.gtk.org gtk网站]下载其源代码。
是一个综合用途的实用的轻量级的C程序库,它提供C语言的常用的数据结构的定义、相关的处理函数,有趣而实用的宏,可移植的封装和一些运行时机能,如事件循环、线程、动态调用、对象系统等的API。
GTK+是可移植的,当然glib也是可移植的,你可以在linux下,也可以在windows下使用它。使用gLib2.0(glib的2.0版本)编写的应用程序,在编译时应该在编译命令中加入pkg-config --cflags --libs glib-2.0
linux GUI
在Linux下开发GUI程序的方法有很多,比如Gnome桌面使用GTK+作为默认的图形界面库,KDE桌面使用Qt作为默认的图形界面库,wxWidgets则是另一个使用广泛的图形库,此外使用Java中的Swing/AWT组件也可以用于开发Linux下的GUI应用。
GTK+
- GTK+最初是为X Window系统开发的,但是目前已经发展成为一个跨平台的图形界面API,其支持的平台包括:Linux Unix Windows Mac OS X
- GTK+基于LGPL协议发布,因此可以将GTK+的二进制动态链接库文件整合到私有软件中而无需额外授权。
- GTK+本身是用C语言编写的,但是可以很方便地通过语言绑定(language binding)和其它语言协同工作
- 与wxWidgets和Qt不同,GTK+支持使用纯C语言进行开发,此外还有一个基于C++的封装项目叫GTKMM。
- GTK+是基于GLib构建的,其中GLib是一个通用的C语言库,类似于C++中的STL,提供了对动态数组、链表、队列、散列表、平衡二叉树、线程操作和XML解析等功能。
在所有的平台上,基于GTK+的应用都看起来完全一样,除非应用了主题。GTK+总是通过主题来模拟原生控件。在Windows平台下,可以通过使用Wimp主题来获得Windows的原生外观。
Qt
Qt是目前使用最广泛的跨平台应用程序框架(Application Framework).
和GTK+一样,Qt并不使用系统提供的控件,而是通过主题模拟这些控件。但是在一些特定的平台,比如Mac OS X和Windows上对于一些最基本的控件通过本地系统调用实现。
Qt通过MOC系统对C++语言进行了扩展,提供了所谓的“信号-槽”(signal-slot)机制。基于信号-槽的事件处理非常优雅,缺点则是是编译系统失去了通用性。
Qt的原生IDE是Qt Creater,同时兼容Qt的其它IDE也非常多,包括Visual Studio、Eclipse、XCode、Edyuk。
wxWidgets
wxWidgets是另一个非常流行的跨平台图形界面库。而GTK+ / Qt不同,wxWidgets并不是通过绘图来模拟控件,而是通过系统本地调用构建完全原生的图形界面。
wxWidgets支持的平台包括:
- wxGTK: 使用Linux下的GTK+构建图形界面
- wxMSW: 使用Win32 API构建图形界面
- wxMac: 使用Mac OS下的Carbon构建图形界面
- wxOSX/Carbon: 使用Mac OS下的Carbon构建图形界面
- wxOSX/Cocoa: 使用Mac OS下的Cocoa构建图形界面
- wxX11: 使用Linux下的X11的通用显示接口构建图形界面
- wxMotif: 使用Linux下的OpenMotif和Lesstif构建图形界面
注意到这里的描述方式有所不同,因为wxWidgets是基于本地接口构建UI的。
在API和编程风格上,wxWidgets和MFC非常相似,但是封装的很多类比MFC更高级。很多知名的MFC程序都会选择用wxWidgets来改写,来快速移植到其它平台,如eMule用wxWidgets移植出aMule和xMule。
除了基本的图形界面、布局、事件系统外,wxWidgets还提供了很多其它的模块,包括:
- wxHTML: 进行HTML渲染
- wxMedia: 对各种多媒体操作提供支持
- wxNet: Socket支持
- wxXML: XML文件读写支持
- wxWidgets集成的功能相对于Qt而言较少,但是足够完成绝大多数的常见任务。