预览加载中,请您耐心等待几秒...
1/8
2/8
3/8
4/8
5/8
6/8
7/8
8/8

在线预览结束,喜欢就下载吧,查找使用更方便

如果您无法下载资料,请参考说明:

1、部分资料下载需要金币,请确保您的账户上有足够的金币

2、已购买过的文档,再次下载不重复扣费

3、资料包下载后请先用软件解压,在使用对应软件打开

实验四多线程聊天室的创建 预备知识: 程序、进程和线程 程序是计算机指令的集合,它以文件的形式存储在磁盘上。 进程:通常被定义为一个正在运行的程序的实例,是一个程序在其自身的地址空间中的一次执行活动。 进程是资源申请、调度和独立运行的单位,因此,它使用系统中的运行资源;而程序不能申请系统资源,不能被系统调度,也不能作为独立运行的单位,因此,它不占用系统的运行资源。 进程由两个部分组成: 1、操作系统用来管理进程的内核对象。内核对象也是系统用来存放关于进程的统计信息的地方。 2、地址空间。它包含所有可执行模块或DLL模块的代码和数据。它还包含动态内存分配的空间。如线程堆栈和堆分配空间。 进程是不活泼的。进程从来不执行任何东西,它只是线程的容器。若要使进程完成某项操作,它必须拥有一个在它的环境中运行的线程,此线程负责执行包含在进程的地址空间中的代码。 单个进程可能包含若干个线程,这些线程都“同时”执行进程地址空间中的代码。 每个进程至少拥有一个线程,来执行进程的地址空间中的代码。当创建一个进程时,操作系统会自动创建这个进程的第一个线程,称为主线程。此后,该线程可以创建其他的线程。 线程运行: 操作系统为每一个运行线程安排一定的CPU时间——时间片。系统通过一种循环的方式为线程提供时间片,线程在自己的时间内运行,因时间片相当短,因此,给用户的感觉,就好像线程是同时运行的一样。 如果计算机拥有多个CPU,线程就能真正意义上同时运行了。 实验步骤: 新建一个基于对话框、支持Windowsockets的MFC可执行应用程序(exe); 设计如图所示界面: 对话框控件ID设置 接收数据框架:IDC_STATIC 接收数据编辑框:IDC_EDIT_RECV 发送数据编辑框:IDC_STATIC IP地址控件:IDC_IPADDRESS1 发送数据编辑框:IDC_EDIT_SEND 发送命令按钮:IDC_BTN_SEND 在MFC中调用AfxSocketInit()加载套接字库,参考MSDN两个版本: 在CWinApp::InitInstance中调用; 在StdAfx.h中包含Afxsock.h头文件 源码: if(!AfxSocketInit()) { AfxMessageBox("加载套接字库失败!"); returnFALSE; } 创建并初始化套接字,为C***Dlg类添加一个private权限SOCKET类型的变量m_socket和一个BOOL类型的InitSocket()成员函数,在OnInitDialog()函数中调用InitSocket()函数实现初始化: 函数实现代码如下: BOOLCCHATDlg::InitSocket() { m_socket=socket(AF_INET,SOCK_DGRAM,0); if(INVALID_SOCKET==m_socket) { MessageBox("套接字创建失败!"); returnFALSE; } SOCKADDR_INaddrSock; addrSock.sin_family=AF_INET; addrSock.sin_port=htons(6000); addrSock.sin_addr.S_un.S_addr=htonl(INADDR_ANY); intretval; retval=bind(m_socket,(SOCKADDR*)&addrSock,sizeof(SOCKADDR)); if(SOCKET_ERROR==retval) { closesocket(m_socket); MessageBox("绑定失败!"); returnFALSE; } returnTRUE; } 实现接收端功能 接收数据的时候会有阻塞,处理方式使用一个单独的线程,采用CreateThread(); (1)先在C***Dlg类的前面定义一个结构体: structRECVPARAM{ SOCKETsock; HWNDhwnd; }; (2)在OnInitDialog()函数中定义一个RECVPARAM类型的指针,然后初始化: RECVPARAM*pRecvParam=newRECVPARAM; pRecvParam->sock=m_socket; pRecvParam->hwnd=m_hWnd; HANDLEhThread=CreateThread(NULL,0,RecvProc, (LPVOID)pRecvParam,0,NULL); CloseHandle(hThread); (3)在C***Dlg类添加函数成员,写线程函数: staticstaticDWORDWINAPIRe