动态链接库 多线程 文件操作 注册表 多媒体编程 Winsock编程(网络编程) 数据库
第11讲 动态链接库 2018年11月19日星期一
动态链接库的基本概念 动态链接库的创建 动态链接库的使用
动态链接库的基本概念 动态链接库(DLLs)是从C语言函数库和Pascal库单元的概念发展而来的。 几乎所有的Windows API都包含在DLL中 是可执行文件,它包含函数,数据或资源等其他应用程序可用到的东西 它可以在需要的时候随时装入, 在装入时或运行时
自从微软推出16位的Windows操作系统起,此后每种版本的Windows操作系统都非常依赖于动态链接库(DLL)中的函数和数据,实际上Windows操作系统中几乎所有的内容都由DLL以一种或另外一种形式代表着。 显示的字体和图标存储在GDI.DLL中 显示Windows桌面和处理用户的输入所需要的代码被存储在一个User.DLL中 Windows编程所需要的大量的API函数也被包含在Kernel.DLL中
静态链接库 多个应用程序,多个静态链接库的副本 占用较多的内存资源 在静态库情况下,函数和数据被编译进一个二进制文件(通常扩展名为*.LIB) Visual C++的编译器在处理程序代码时将从静态库中恢复这些函数和数据并把他们和应用程序中的其他模块组合在一起生成可执行文件
"静态链接",此时因为应用程序所需的全部内容都是从库中复制了出来,所以静态库本身并不需要与可执行文件一起发行
DLL可在函数调用其中的函数时,才被装入内存 减少了内存和磁盘空间 DLL是包含若干函数、类或资源的库文件 函数和数据被存储在一个DLL上 ,可供其它DLL或应用程序使用
DLL的优点 共享DLL,节省内存,减少动态交换 不同程序设计语言之间可以共享DLL 减少可执行代码大小 重用代码 大工程可分为易管理的小工程 实现新功能更容易、软件升级
引入库文件包含被DLL导出的函数的名称和位置 DLL包含实际的函数和数据 应用程序使用LIB文件链接到所需要使用的DLL文件 在动态库的情况下,有两个文件 引入库(.LIB)文件 DLL文件 引入库文件包含被DLL导出的函数的名称和位置 DLL包含实际的函数和数据 应用程序使用LIB文件链接到所需要使用的DLL文件
动态链接库的创建 Win32 Dynamic-Link Library方式 微软的Visual C++支持三种DLL 使用导出函数关键字_declspec(dllexport)创建 用.def文件创建 微软的Visual C++支持三种DLL Non-MFC Dll(非MFC动态库) Regular Dll(常规DLL) Extension Dll(扩展DLL)
Win32 Dynamic-Link Library方式 (1)使用导出函数关键字_declspec(dllexport)创建 //Win32DLL.h extern "C" _declspec(dllexport) int Max(int a, int b); extern "C" _declspec(dllexport) int Min(int a, int b); //Win32DLL.cpp #include"Win32DLL.h" int Max(int a, int b) { return (a>=b)?a:b; } int Min(int a, int b) return (a<=b)?a:b;
查看Debug目录,生成了两个文件 Win32DLL.dll Win32DLL.lib
(2)用.def文件创建 删除头文件和实现文件中的包含部分 建立一个新文本文件Win32DLL_DEF.def
DEF文件的格式 LIBRARY Win32DLL_Def EXPORTS Max :Max@1 Min :Min@2 其中LIBRARY语句说明该def文件是属于相应DLL的, EXPORTS语句下列出要导出的函数名称。 我们可以在.def文件中的导出函数后加@n,如Max@1,Min@2, 表示要导出的函数顺序号,在进行显式连时可以用到它。 该DLL编译成功后,打开工程中的Debug目录, 同样也会看到MyDll.dll和MyDll.lib文件。
实现文件 //Win32DLL_DEF.cpp int Max(int a, int b) { return (a>=b)?a:b; } int Min(int a, int b) return (a<=b)?a:b;
MFC AppWizard[dll]方式生成常规/扩展DLL 常规DLL静态链接到MFC 常规DLL动态链接到MFC MFC扩展DLL
MFC生成框架 可以使用MFC类 其它与Non-MFC大同小异
DLL的发布 *.h *.lib *.dll
DLL的使用 隐式链接 显式链接
要先将MyDll.dll和MyDll.lib拷贝到某目录下面 Windows系统将遵循下面的搜索顺序来定位DLL: 1.包含EXE文件的目录 2.进程的当前工作目录 3.Windows系统目录 4.Windows目录 5.列在Path环境变量中的一系列目录
隐式链接 _declspec(dllimport) //*.h #include"Dlltest.h" … #pragma comment(lib,"MyDll.lib") extern "C"_declspec(dllimport) int Max(int a,int b); extern "C"_declspec(dllimport) int Min(int a,int b); //*.cpp #include"Dlltest.h" … Int x=Min(100,200);
显式链接 显式链接是应用程序在执行过程中随时可以加载DLL文件,也可以随时卸载DLL文件,这是隐式链接所无法作到的,所以显式链接具有更好的灵活性,对于解释性语言更为合适。 实现显式链接要麻烦一些。
跟显式链接相关的函数 HINSTANCE LoadLibrary( LPCTSTR lpLibFileName); FARPROC GetProcAddress( HMODULE hModule, LPCSTR lpProcName); BOOL FreeLibrary( HMODULE hLibModule);
typedef int(*pMax)(int a,int b); typedef int(*pMin)(int a,int b); HINSTANCE hDLL; pMax Max; hDLL=LoadLibrary("Win32DLL.dll");//加载动态链接库Win32DLL.dll文件; if(!hDLL) { MessageBox("装入动态链接库失败!"); return ; } Max=(pMax)GetProcAddress(hDLL,"Max"); if(!Max) MessageBox("获取函数地址失败!"); int A=Max(5,8); CString x; x.Format("较大数是%d!",A); MessageBox(x); if(!FreeLibrary(hDLL))//卸载Win32DLL.dll文件; MessageBox("关闭Win32DLL.dll失败");
使用显式链接应用程序编译时不需要使用相应的Lib文件 关键字typedef,定义指向和DLL中相同的函数原型指针 GetProcAddress(hDLL,“Min”)改为 GetProcAddress(hDLL, MAKEINTRESOURCE(2))
dumpbin usage: DUMPBIN [options] [files] options: /ALL /ARCH /ARCHIVEMEMBERS /DEPENDENTS /DIRECTIVES /DISASM /EXPORTS /FPO /HEADERS /IMPORTS /LINENUMBERS /LINKERMEMBER[:{1|2}] /LOADCONFIG /OUT:filename /PDATA /RAWDATA[:{NONE|BYTES|SHORTS|LONGS}[,#]] /RELOCATIONS /SECTION:name /SUMMARY /SYMBOLS
DLL的概述 DLL的创建 DLL的使用
第12讲 多线程
程序Program 进程Process 线程Thread
线程的创建 HANDLE CreateThread( LPSECURITY_ATTRIBUTES lpThreadAttributes, // pointer to security attributes DWORD dwStackSize, // initial thread stack size LPTHREAD_START_ROUTINE lpStartAddress, // pointer to thread function LPVOID lpParameter, // argument for new thread DWORD dwCreationFlags, // creation flags LPDWORD lpThreadId // pointer to receive thread ID );
线程的终止 VOID ExitThread( DWORD dwExitCode // exit code for this thread ); HANDLE GetCurrentProcess(VOID) BOOL TerminateThread( HANDLE hThread, // handle to the thread DWORD dwExitCode // exit code for the thread );
线程的挂起 DWORD SuspendThread( HANDLE hThread // handle to the thread );
线程的恢复 DWORD ResumeThread( HANDLE hThread // identifies thread to restart );
线程类 CWinThread
第13讲 文件操作
文本文件 二进制文件
1. BMP文件组成 BMP文件由文件头、位图信息头、颜色信息和图形数据四部分组成。文件头主要包含文件的大小、文件类型、图像数据偏离文件头的长度等信息;位图信息头包含图象的尺寸信息、图像用几个比特数值来表示一个像素、图像是否压缩、图像所用的颜色数等信息。颜色信息包含图像所用到的颜色表,显示图像时需用到这个颜色表来生成调色板,但如果图像为真彩色,既图像的每个像素用24个比特来表示,文件中就没有这一块信息,也就不需要操作调色板。文件中的数据块表示图像的相应的像素值,需要注意的是:图像的像素值在文件中的存放顺序为从左到右,从下到上,也就是说,在BMP文件中首先存放的是图像的最后一行像素,最后才存储图像的第一行像素,但对与同一行的像素,则是按照先左边后右边的的顺序存储的;另外一个需要读者朋友关注的细节是:文件存储图像的每一行像素值时,如果存储该行像素值所占的字节数为4的倍数,则正常存储,否则,需要在后端补0,凑足4的倍数。
2. BMP文件头 BMP文件头数据结构含有BMP文件的类型、文件大小和位图起始位置等信息。其结构定义如下: typedef struct tagBITMAPFILEHEADER { WORD bfType; // 位图文件的类型,必须为"BM" DWORD bfSize; // 位图文件的大小,以字节为单位 WORD bfReserved1; // 位图文件保留字,必须为0 WORD bfReserved2; // 位图文件保留字,必须为0 DWORD bfOffBits; // 位图数据的起始位置,以相对于位图文件头的偏移量表示,以字节为单位 } BITMAPFILEHEADER;该结构占据14个字节。
3. 位图信息头 BMP位图信息头数据用于说明位图的尺寸等信息。其结构如下: typedef struct tagBITMAPINFOHEADER{ DWORD biSize; // 本结构所占用字节数 LONG biWidth; // 位图的宽度,以像素为单位 LONG biHeight; // 位图的高度,以像素为单位 WORD biPlanes; // 目标设备的平面数不清,必须为1 WORD biBitCount// 每个像素所需的位数,必须是1(双色), 4(16色),8(256色)或24(真彩色)之一 DWORD biCompression; // 位图压缩类型,必须是 0(不压缩),1(BI_RLE8压缩类型)或2(BI_RLE4压缩类型)之一 DWORD biSizeImage; // 位图的大小,以字节为单位 LONG biXPelsPerMeter; // 位图水平分辨率,每米像素数 LONG biYPelsPerMeter; // 位图垂直分辨率,每米像素数 DWORD biClrUsed;// 位图实际使用的颜色表中的颜色数 DWORD biClrImportant;// 位图显示过程中重要的颜色数 } BITMAPINFOHEADER;该结构占据40个字节。 注意:对于BMP文件格式,在处理单色图像和真彩色图像的时候,无论图象数据多么庞大,都不对图象数据进行任何压缩处理,一般情况下,如果位图采用压缩格式,那么16色图像采用RLE4压缩算法,256色图像采用RLE8压缩算法。
4. 颜色表 颜色表用于说明位图中的颜色,它有若干个表项,每一个表项是一个RGBQUAD类型的结构,定义一种颜色。RGBQUAD结构的定义如下: typedef struct tagRGBQUAD { BYTErgbBlue;// 蓝色的亮度(值范围为0-255) BYTErgbGreen; // 绿色的亮度(值范围为0-255) BYTErgbRed; // 红色的亮度(值范围为0-255) BYTErgbReserved;// 保留,必须为0 } RGBQUAD; 颜色表中RGBQUAD结构数据的个数由BITMAPINFOHEADER 中的biBitCount项来确定,当biBitCount=1,4,8时,分别有2,16,256个颜色表项,当biBitCount=24时,图像为真彩色,图像中每个像素的颜色用三个字节表示,分别对应R、G、B值,图像文件没有颜色表项。位图信息头和颜色表组成位图信息,BITMAPINFO结构定义如下: typedef struct tagBITMAPINFO { BITMAPINFOHEADER bmiHeader; // 位图信息头 RGBQUAD bmiColors[1]; // 颜色表 } BITMAPINFO; 注意:RGBQUAD数据结构中,增加了一个保留字段rgbReserved,它不代表任何颜色,必须取固定的值为"0",同时, RGBQUAD结构中定义的颜色值中,红色、绿色和蓝色的排列顺序与一般真彩色图像文件的颜色数据排列顺序恰好相反,既:若某个位图中的一个像素点的颜色的描述为"00,00,ff,00",则表示该点为红色,而不是蓝色。
5. 位图数据 位图数据记录了位图的每一个像素值或该对应像素的颜色表的索引值,图像记录顺序是在扫描行内是从左到右,扫描行之间是从下到上。这种格式我们又称为Bottom_Up位图,当然与之相对的还有Up_Down形式的位图,它的记录顺序是从上到下的,对于这种形式的位图,也不存在压缩形式。位图的一个像素值所占的字节数:当biBitCount=1时,8个像素占1个字节;当biBitCount=4时,2个像素占1个字节;当 biBitCount=8时,1个像素占1个字节;当biBitCount=24时,1个像素占3个字节,此时图像为真彩色图像。当图像不是为真彩色时,图像文件中包含颜色表,位图的数据表示对应像素点在颜色表中相应的索引值,当为真彩色时,每一个像素用三个字节表示图像相应像素点彩色值,每个字节分别对应R、G、B分量的值,这时候图像文件中没有颜色表。上面我已经讲过了,Windows规定图像文件中一个扫描行所占的字节数必须是4的倍数(即以字为单位),不足的以0填充,图像文件中一个扫描行所占的字节数计算方法: DataSizePerLine= (biWidth* biBitCount+31)/8;// 一个扫描行所占的字节数 位图数据的大小按下式计算(不压缩情况下): DataSize= DataSizePerLine* biHeight。 上述是BMP文件格式的说明,搞清楚了以上的结构,就可以正确的操作图像文件,对它进行读或写操作了。
看一个位图处理的例子
FILE CFile CStdioFile
第14讲 注册表
注册表的结构和作用 注册表操作函数 注册表操作实例
注册表的结构和作用
HKEY_CLASS_ROOT:文件扩展名的信息 HKEY_CURRENT_USER:当前用户的信息 HKEY_LOCAL_MACHINE:本机软硬件配置信息 HKEY_USERS:所有用户信息 HKEY_CURRENT_CONFIG:计算机的当前配置 HKEY_DYN_DATA:内存中的需要快速更新和检索的数据
注册表操作函数 打开注册表 关闭注册表 从注册表中取得数据 设置注册表中的键值 建立并打开制定的关键字 枚举每一个子关键字
打开一个键的函数:RegOpenKeyEx 函数定义:LONG RegOpenKeyEx( 打开注册表 打开一个键的函数:RegOpenKeyEx 函数定义:LONG RegOpenKeyEx( HKEY hKey, //已经打开的键的句柄,或者直接是上述几个根键 LPCTSTR lpSubKey, //要打开的子键名字的地址 DWORD ulOptions, //保留值,必须为0 REGSAM samDesired, //打开方式,如读还是写 PHKEY phkResult //返回的打开的子键的句柄 );
查询某一个键值:RegQueryValueEx 函数定义:LONG RegQueryValueEx( HKEY hKey,//要查询的键的句柄 LPCTSTR lpValueName,//要查询的键值的名称 LPDWORD lpReserved,//保留值 LPDWORD lpType,//要查询的数据的类型 LPBYTE lpData,//要返回的查询的数据 LPDWORD lpcbData//预置的数据的长度 );
设置一个键值RegSetValueEx 函数定义:LONG RegSetValueEx( HKEY hKey,//要设置的键的句柄 LPCTSTR lpValueName,//要访问的键值的名称 LPDWORD lpReserved,//保留值 DWORD dwType,//要设置的数据的类型 const BYTE *lpData,//要设置的健值 DWORD cbData//数据的长度 );
关闭 LONG RegCloseKey(HKEY hKey);
例子
第15讲 多媒体编程 2018年11月19日星期一
媒体控制接口(MCI) MCI在控制音频、视频等设备方面,提供了与设备无关的API接口。 用户应用程序可使用MCI控制标准多媒体设备 Multimedia Control Interface MCI在控制音频、视频等设备方面,提供了与设备无关的API接口。 用户应用程序可使用MCI控制标准多媒体设备 不同设备其驱动控制方式不同: 一些MCI设备驱动程序(影碟机)直接控制目标设备; 一些MCI设备驱动程序(MIDI函数)可使用MMSYSTEM函数间接控制目标设备; 还有一些MCI设备驱动程序(影片演播器)则提供了与其他Windows DLL的高层接口。
应用程序通过设备的类型来区分设备 。 如果要通过MCI去控制设备,必须将相应的MCI驱动程序和设备的驱动程序,DLL(如果需要)装入。 MCI驱动程序的安装可通过Windows中的控制面板来完成。在Windows中SYSTEM.INI文件中的〔mci〕部分包括了一个已安装了的设备类型表 。
设备类型 设备类型 描 述 cdaudio dat digitalvideo mmmovie other overlay scanner vcr videodisc waveaudio 激光唱机、CD-ROM 数字化磁带音频播放机 窗口中的数字视频(非基于GUI) 多媒体影片演播器 未定义的MCI设备 叠加设备(窗口中的模拟视频) 图像扫描仪 磁带录相机或播放机 影碟机 播放数字化波形文件的音频设备
Windows提供的MCI设备驱动程序 设备类型 设备驱动程序名 描 述 cdaudio mmmovie sequencer 描 述 cdaudio mmmovie sequencer videodisc waveaudio MCICDA.DRV MCIMMP.DRV MCISEQ.DRV MCIPIONR.DRV MCIWAVE.DRV 一个播放光盘音频的MCI设备驱动程序 一个播放多媒体影片文件的MCI设备驱动程序 一个播放MIDI音频文件的MCI设备驱动程序 一个播放先锋LD-V4200影碟机文件的MCI设备驱动程序 一个播放和记录波形音频文件的MCI设备驱动程序
MCI命令消息接口 mciSendCommand mciSendString mciGetDeviceID mciGetErrorString mciSetYieldProc mciGetYieldProc
mciSendCommand发送命令消息 DWORD mciSendCommand(WORD DeviceID,WORD Message,DWORD Param1,DWORD Param2) DeviceID标识一个MCI设备; Message 标识要发出的消息,如MCI-OPEN等; Param1 为消息指定标志; Param2 为指定一个指向消息数据结构的指针。 该函数调用如果成功返回0,否则返回一个错误代码, mciGetErrorString 可获得对这个错误的文本描述。
MCI命令消息分类 直接由MCI解释的命令 由所有的MCI设备所支持的命令 基本命令 扩展命令
直接由MCI解释的命令 消 息 描 述 MCI-SYSINFO MCI-BREAK MCI-SOUND 返回有关MCI设备的信息 消 息 描 述 MCI-SYSINFO MCI-BREAK MCI-SOUND 返回有关MCI设备的信息 为指定的MCI设备设置一个中止键 播放一段在WIN.INI文件中的〔Sounds〕部分所指定的系统声音
所有的MCI设备支持的命令消息 消 息 描 述 关闭一个MCI设备 MCI-GETDEVCAPS 获得一个MCI设备的性能 MCI-INFO 消 息 描 述 MCI-CLOSE MCI-GETDEVCAPS MCI-INFO MCI-OPEN MCI-STATUS 关闭一个MCI设备 获得一个MCI设备的性能 从一个MCI设备中得到有关的信息 初始化一个MCI设备 从一个MCI设备返回有关的状态信息
基本命令消息 消 息 描 述 MCI_LOAD MCI_PAUSE MCI_PLAY MCI_RECORD MCI_RESUME 消 息 描 述 MCI_LOAD MCI_PAUSE MCI_PLAY MCI_RECORD MCI_RESUME MCI_SAVE MCI_SEEK MCI_SET MCI_STATUS MCI_STOP 从一个磁盘文件加载数据 暂停播放或记录 开始传送输出数据 开始传送输入数据 重新开始播放或记录 将数据存储到磁盘文件中 向前或向后检索 设置设备信息 从一个MCI设备返回有关的状态信息停止播放或记录
使用多媒体设备的基本步骤 打开 MCI_OPEN 设置或获取 MCI_SET MCI_STATUS 操作 MCI_XXX 关闭 MCI_CLOSE
打开一个设备 使用设备之前,必须使用MCI_OPEN命令消息来初始化该设备 打开MCI设备的方法有以下几种: (2)用MCI设备驱动程序名指定待打开的MCI设备 (3)用设备类型常数(见下表)指定待打开的MCI设备 (4)仅用设备元素指定打开的复合设备
设备类型及常数 设备类型 常 数 animation cdaudio dat digitalvideo other overlay 常 数 animation cdaudio dat digitalvideo other overlay scanner vcr sequencer videodisc waveaudio MCI_DEVTYPE_ANIMATION MCI_DEVTYPE_CD_AUDIO MCI_DEVTYPE_DAT MCI_DEVTYPE_DIGITAL_VIDEO MCI_DEVTYPE_OTHER MCI_DEVTYPE_OVERLAY MCI_DEVTYPE_SCANNER MCI_DEVTYPE_VIDEOTAPE MCI_DEVTYPE_SEQUENCER MCI_DEVTYPE_VIDEODISC MCI_DEVTYPE_WAVEFORM_AUDIO
例如:打开一个CD设备 // 打开设备 MCI_OPEN_PARMS OpenParms; OpenParms.lpstrDeviceType = (LPCSTR) MCI_DEVTYPE_CD_AUDIO; OpenParms.wDeviceID = 0; if (mciSendCommand (NULL, MCI_OPEN, MCI_WAIT | MCI_OPEN_TYPE | MCI_OPEN_TYPE_ID | MCI_OPEN_SHAREABLE, (DWORD)(LPVOID) &OpenParms)) return FALSE; m_wDeviceID = OpenParms.wDeviceID;
MCI_OPEN_PARMS结构 typedef struct tagMCI_OPEN_PARMSA { DWORD dwCallback; MCIDEVICEID wDeviceID; LPCSTR lpstrDeviceType; LPCSTR lpstrElementName; LPCSTR lpstrAlias; } MCI_OPEN_PARMS;
关闭一个设备 MCI_CLOSE命令消息取消对一个设备或者设备元素的访问,它类似于一个文件的关闭操作。
关闭设备 mciSendCommand (m_wDeviceID, MCI_CLOSE, MCI_WAIT, NULL);
命令字符串接口-一个操作用一个字符串描述 使用命令字符串接口3个函数: mciSendString向一个MCI设备驱动程序发送一个命令字符串。这个函数同时也具有对于回调函数和返回字符串的参数。 mciGetErrorString返回一个同错误代码相对应的错误字符串。 mciExecute向一个MCI设备驱动程序发送一个命令字符串。
以上是管理多媒体设备的基本命令 下面来看一看CD播放器的开发 简单方法 Visual Basic 复杂方法 Visual C++
第16讲 Winsock编程 2018年11月19日星期一
基于WINDOWS SOCKET的应用开发介绍 WINSOCK API主要函数简介 聊天应用程序的设计说明 服务器端 客户端
SOCKET简介 进程间通信方式 80年代初,美国政府的高级研究工程机构(ARPA)给加利福尼亚大 学Berkeley分校提供了资金,让他们在UNIX操作系统下实现TCP/IP协议。 研究人员为TCP/IP网络通信开发了一个API。这个API称为Socket接口(套接字)。今天,SOCKET接口 是TCP/IP网络最为通用的API,也是在INTERNET上进行应用开发最为通 用的API。
90年代初,由Microsoft联合了其他几家公司共同 制定了一套WINDOWS下的网络编程接口,即WindowsSockets规范。 从 1991年的1.0版到1995年的2.0.8版,经过不断完善并在Intel、 Microsoft、Sun、SGI、Informix、Novell等公司的全力支持下,已成 为Windows网络编程的事实上的标准。
在实际应用中的 WINDOWSSOKCETS规范主要有1. 1版和2. 2版。两者的最重要区别是1. 1版 只支持TCP/IP协议,而2 SOCKET实际在计算机中提供了一个通信端口,可以通过这个端口 与任何一个具有SOCKET接口的计算机通信。应用程序在网络上传输,接 收的信息都通过这个SOCKET接口来实现。在应用开发中就像使用文件句 柄一样,可以对SOCKET句柄进行读写操作。
平台 Wi n s o c k版本 Windows 95 1 . 1(2 . 2) Windows 98 2 . 2 Windows NT 4.0 2 . 2 Windows 2000 2 . 2
基于WINDOWS SOCKET的应用开发介绍 在WINDOWS系统中进行WINSOCK开发使用的编程语言有很多, VC++,JAVA,DELPHI,VB等。 VC++用得较多,跟WinSocket联系最紧密
MFC对WinSocket的封装 CAsynSocket Csocket CSocketFile等
WinSocket API 在VC中进行WINSOCK的API编程开发,需要使用到下面三个文件: WINSOCK.H: 这是WINSOCK API的头文件。 WSOCK32.LIB: WINSOCK API连接库文件。在使用中,要把它作为项目 的非缺省的连接库包含到项目文件中去。 WINSOCK.DLL: WINSOCK的动态连接库,位于WINDOWS的安装目录下。
服务器 /客户机 面向连接的、可靠的(TCP) 无连接的、不可靠的(UDP) 一般在使用中,面向连接协议的SOCKET编程模型应用最为广泛,因 为面向连接协议提供了一系列的数据纠错功能,可以保证在网络上传输 的数据及时、无误地到达对方。
面向连接的协议Socket模型
面向无连接的协议Socket模型
使用SOCKET接口(面向连接或无连接)进行网络通信时, 必须按下面的四步进行处理: 2、程序必须按要求配置此SOCKET。也就是说,程序要么将此 SOCKET连接到远方的主机上,要么给此SOCKET指定一个 本地协议端口。 3、程序必须按要求通过此SOCKET发送和接收数据。 4、程序必须关闭此SOCKET。
WINSOCK API主要函数简介 WSAStartup WSACleanup socket closesocket bind listen accept connect recv recvfrom send sendto
WSAStartup 连结应用程序与 Windows Sockets DLL 的第一个函数 此函数是应用程序调用 Windows Sockets DLL函数中的第一个,此函数调用成功后,才可以再调用其他 Windows Sockets DLL 的函数。
int WSAStartup ( WORD wVersionRequested, LPWSADATA lpWSAData ); wVersionRequested 是WinSocket API提供的调用方可使用的最高版本号,高字节是副版本号,低字节是主版本号 lpWSAData 是指向WSADATA的指针,用来接收Socket的实现细节
WSACleanup 结束 Windows Sockets DLL 的使用 int WSACleanup();
socket SOCKET socket ( int af, int type, int protocol ); af为PF_INET,表示互联网协议组 type,套接字的类型 SOCK_STREAM SOCK_DGRAM protocol,套接字所使用的协议
closesocket int closesocket ( SOCKET s );
bind int bind ( SOCKET s, const struct sockaddr FAR* name, int namelen ); 一旦为某种特定协议创建了套接字,就必须将套接字绑定到一个已知地址。bind函数可将指定的套接字同一个已知地址绑定到一起。
accept SOCKET accept ( SOCKET s, struct sockaddr FAR* addr, int FAR* addrlen ); 服务器接收客户的连接请求,在建立好输入队列以后,服务器就调用accept,然后进入休眠状态,等待用户的连接请求
connect int connect ( SOCKET s, const struct sockaddr FAR* name, int namelen ); 要求连接某一Socket到指定的网络上服务端。 此函数用在客户端,用来向服务端要求建立连接。当连接建立完成后,客户端即可利用此 Socket 来与服务端进行信息传递。
recv recvfrom int recv ( SOCKET s, char FAR* buf, int len, int flags ); int recvfrom ( SOCKET s, char FAR* buf, int len, int flags, struct sockaddr FAR* from, int FAR* fromlen );
send sendto int send ( SOCKET s, const char FAR * buf, int len, int flags ); int sendto ( SOCKET s, const char FAR * buf, int len, int flags, const struct sockaddr FAR * to, int tolen );
看例子 聊天程序 服务器/客户机 Server/Client 面向连接的(TCP)