第17课 进程间通信

 

17 进程间通信

有四种方法

1.剪贴板

a.创建个ClipBoard的对话框应用程序,加两EditBox和两个Button发送接收。

b.具体代码:

    发送端代码:

if(OpenClipboard())

{

CString str;

HANDLE hClip;

char *pBuf;

EmptyClipboard();

GetDlgItemText(IDC_EDIT_SEND,str);

hClip=GlobalAlloc(GMEM_MOVEABLE,str.GetLength()+1);

pBuf=(char*)GlobalLock(hClip);将句柄转换为指针!

strcpy(pBuf,str);

GlobalUnlock(hClip);

SetClipboardData(CF_TEXT,hClip);

CloseClipboard();

}

     接收端代码:

if(OpenClipboard())

{

if(IsClipboardFormatAvailable(CF_TEXT))

{

   HANDLE hClip;

   char *pBuf;

   hClip=GetClipboardData(CF_TEXT);

   pBuf=(char*)GlobalLock(hClip);

   GlobalUnlock(hClip);

   SetDlgItemText(IDC_EDIT_RECV,pBuf);

   CloseClipboard();

}

}

2.匿名管道:只能在父子进程之间进行通信

a.先建一个Parent的单文档应用程序,增加“创建管道”“读取数据”“写入数据”三个菜单

b.增加成员变量HANDLE类型的hRead,hWrite,初始化变量,并在析构函数中释放句柄

c.响应菜单代码:

void CParentView::OnPipeCreate() 菜单“创建管道”代码

{

// TOD Add your command handler code here

SECURITY_ATTRIBUTES sa;

sa.bInheritHandle=TRUE;

sa.lpSecurityDescriptor=NULL;

sa.nLength=sizeof(SECURITY_ATTRIBUTES);

if(!CreatePipe(&hRead,&hWrite,&sa,0))

{

MessageBox("创建匿名管道失败!");

return;

}

STARTUPINFO sui;

PROCESS_INFORMATION pi;

ZeroMemory(&sui,sizeof(STARTUPINFO));将数据清0

sui.cb=sizeof(STARTUPINFO);

sui.dwFlags=STARTF_USESTDHANDLES;

sui.hStdInput=hRead;

sui.hStdOutput=hWrite;

sui.hStdError=GetStdHandle(STD_ERROR_HANDLE);

if(!CreateProcess("..//Child//Debug//Child.exe",NULL,NULL,NULL,

   TRUE,0,NULL,NULL,&sui,&pi))创建子进程

{

CloseHandle(hRead);

CloseHandle(hWrite);关闭句柄,将内核对象的使用计数减少1,这样当操作系统发现内核对象的使用计数为0时,将清除内核对象。

hRead=NULL;

hWrite=NULL;

MessageBox("创建子进程失败!");

return;

}

else

{

CloseHandle(pi.hProcess);

CloseHandle(pi.hThread);

}

}

void CParentView::OnPipeRead() 菜单“读取数据”代码

{

// TOD Add your command handler code here

char buf[100];

DWORD dwRead;

if(!ReadFile(hRead,buf,100,&dwRead,NULL))

{

MessageBox("读取数据失败!");

return;

}

MessageBox(buf);

}

void CParentView::OnPipeWrite() 菜单“写入数据”代码

{

// TOD Add your command handler code here

char buf[]="http://www.sunxin.org";

DWORD dwWrite;

if(!WriteFile(hWrite,buf,strlen(buf)+1,&dwWrite,NULL))

{

MessageBox("写入数据失败!");

return;

}

}

     d.再建一个Child的单文档,在View中增加两个成员hReadhWrite.OnInitialUpdate()中得到句柄的值。

void CChildView::OnInitialUpdate()

{

CView::OnInitialUpdate();

// TOD Add your specialized code here and/or call the base class

hRead=GetStdHandle(STD_INPUT_HANDLE);注意这句代码!

hWrite=GetStdHandle(STD_OUTPUT_HANDLE);

}

     e.加菜单“读取数据”“写入数据”其代码如下:

void CChildView::OnPipeRead()

{

// TOD Add your command handler code here

char buf[100];

DWORD dwRead;

if(!ReadFile(hRead,buf,100,&dwRead,NULL))

{

MessageBox("读取数据失败!");

return;

}

MessageBox(buf);

}

void CChildView::OnPipeWrite()

{

// TOD Add your command handler code here

char buf[]="匿名管道测试程序";

DWORD dwWrite;

if(!WriteFile(hWrite,buf,strlen(buf)+1,&dwWrite,NULL))

{

MessageBox("写入数据失败!");

return;

}

}

3.命名管道:还可以跨网络通信,服务器只能在win2000NT下运行!而客户端可以在95下运行。关键函数CreateNamedPipe

a.先建一个NamedPipeSRV单文档应用程序,加菜单“创建管道”“读取数据”“写入数据”

b.View中增加Handle变量hPipe,注意在析构函数中释放它!

c.响应菜单,创建命名管道

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值