日期:2014-05-18  浏览次数:21058 次

C#管道通讯
想请教下C#自带的管道通讯命名空间:using System.IO.Pipes;它其中包含两个客户端和服务端两个类:


做了个小测试,新建了连个项目,一个作为服务端,一个作为客户端,如下,是将各自的textBox中的值传到对方listBox并显示:


现在的问题是这样的:管道连接之后,单单从服务端(客户端)向客户端(服务端)发消息是可以的;如果先从服务端向客户端发送,再让客户端向服务端发送,则会卡死在客户端的Write过程(或如果先从客户端向服务端发送,再让服务端向客户端发送,则会卡死在服务端的Write过程),我的做法是停止当前管道连接,再重新新建一个管道连接才能发(有点扯蛋)……

对于MSDN中说的客户端和服务端之间支持异步操作,我不是太理解,是不是说仅仅需要连接一次,彼此都可以进行读写而不要重新关闭管道,再连上?我在网上搜了很多例子都是单向发的……重关管道再连,貌似是个不太好的方式。

如果大家知道管道仅连接一次,以后就可以实现互相收发,还请贴下代码……

服务端主要代码是:
C# code

        //服务端向客户端发送
        private void button1_Click(object sender, EventArgs e)
        {
            Thread SendData=new Thread(new ThreadStart(WriteData));
            SendData.Start();
        }

        private void WriteData()
        {
            try
            {
                    this.listBox1.Items.Add("开始连接管道……");
                    pipeServer =new NamedPipeServerStream("testpipe", PipeDirection.InOut, 2);                    
                    pipeServer.WaitForConnection();
                    Thread.Sleep(1000);
                    if (pipeServer.IsConnected)
                    {
                        this.listBox1.Items.Add("与客户端连接成功^_^");
                        StreamWriter sw = new StreamWriter(pipeServer);                        
                        sw.WriteLine(this.textBox1.Text);
                        sw.Flush();
                        Thread.Sleep(1000);
                        sw.Close();
                    }
                    else
                    {
                        this.listBox1.Items.Add("与客户端连接失败(⊙_⊙)");
                    }
            }
            catch (Exception error)
            {
                this.listBox1.Items.Add(error.Message + "写数据时发生错误!");
            }
        }
        //服务端从客户端接收数据
        private void button2_Click(object sender, EventArgs e)
        {
            ReceiveDataThread = new Thread(new ThreadStart(ReceiveDataFromClient));
            ReceiveDataThread.Start();
        }

        private void ReceiveDataFromClient()
        {
            while (true)
            {
                try
                {
                    pipeServer = new NamedPipeServerStream("testpipe", PipeDirection.InOut, 2);
                    pipeServer.WaitForConnection();//等待
                    StreamReader sr = new StreamReader(pipeServer);
                    string recData = sr.ReadLine();
                    this.listBox1.Items.Add(recData);
                    Thread.Sleep(1000);
                    sr.Close();
                }
                catch (Exception)
                {                    
                    throw;
                }
                if (tag==1)
                {
                    break;
                }
            }
        }



客户端主要代码:
C# code

        //客户端向服务端发数据
        private void button1_Click(object sender, EventArgs e)
        {
            Thread WriteData = new Thread(new ThreadStart(SendData));
            WriteData.Start();
        }

        private void SendData()
        {
            try
            {
                pipeClientA = new NamedPipeClientStream(@"\\.", "testpipe",
PipeDirection.InOut, PipeOptions.None,
TokenImpersonationLevel.Impersonation);
                pipeClientA.Connect();
                StreamWriter sw = new StreamWriter(pipeClientA);
                sw.WriteLine(this.textBox1.Text);
                sw.Flush();
                Thread.Sleep(1000);
                sw.Close();
            }
            catch (Exception)
            {                
                throw;
            }            
        }