zoukankan      html  css  js  c++  java
  • 基于C#的UDP协议的异步实现

    一、摘要

      总结UDP传输协议的异步实现。

    二、实验平台

      visual studio 2010

    三、实验实例

      服务器端代码:

    复制代码
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Net;
    using System.Net.Sockets;
    using System.Threading;
    namespace AsyncServer
    {
        // 定义 UdpState类
        public class UdpState
        {
            public UdpClient udpClient;
            public IPEndPoint ipEndPoint;
            public const int BufferSize = 1024;
            public byte[] buffer = new byte[BufferSize];
            public int counter = 0;
        }
        // 异步UDP类
        public class AsyncUdpSever
        {
            // 定义节点
            private IPEndPoint ipEndPoint = null;
            private IPEndPoint remoteEP = null;
            // 定义UDP发送和接收
            private UdpClient udpReceive = null;
            private UdpClient udpSend = null;
            // 定义端口
            private const int listenPort = 1100;
            private const int remotePort = 1101;
            UdpState udpReceiveState = null;
            UdpState udpSendState = null;
            // 异步状态同步
            private ManualResetEvent sendDone = new ManualResetEvent(false);
            private ManualResetEvent receiveDone = new ManualResetEvent(false);
            public AsyncUdpSever()
            {
                // 本机节点
                ipEndPoint = new IPEndPoint(IPAddress.Any, listenPort);
                // 远程节点
                remoteEP = new IPEndPoint(Dns.GetHostAddresses(Dns.GetHostName())[0], remotePort);
                // 实例化
                udpReceive = new UdpClient(ipEndPoint);
                udpSend = new UdpClient();
    
                // 分别实例化udpSendState、udpReceiveState
                udpReceiveState = new UdpState();
                udpReceiveState.udpClient = udpReceive;
                udpReceiveState.ipEndPoint = ipEndPoint;
    
                udpSendState = new UdpState();
                udpSendState.udpClient = udpSend;
                udpSendState.ipEndPoint = remoteEP;
            }
            public void ReceiveMsg()
            {
                Console.WriteLine("listening for messages");
                while (true)
                {
                    lock (this)
                    {
                        // 调用接收回调函数
                        IAsyncResult iar = udpReceive.BeginReceive(new AsyncCallback(ReceiveCallback), udpReceiveState);
                        receiveDone.WaitOne();
                        Thread.Sleep(100);
                    }
                }
            }
            // 接收回调函数
            private void ReceiveCallback(IAsyncResult iar)
            {
                UdpState udpReceiveState = iar.AsyncState as UdpState;
                if (iar.IsCompleted)
                {
                    Byte[] receiveBytes = udpReceiveState.udpClient.EndReceive(iar, ref udpReceiveState.ipEndPoint);
                    string receiveString = Encoding.ASCII.GetString(receiveBytes);
                    Console.WriteLine("Received: {0}", receiveString);
                    //Thread.Sleep(100);
                    receiveDone.Set();
                    SendMsg();
                }
            }
            // 发送函数
            private void SendMsg()
            {
                udpSend.Connect(udpSendState.ipEndPoint);
                udpSendState.udpClient = udpSend;
                udpSendState.counter++;
    
                string message = string.Format("第{0}个UDP请求处理完成!", udpSendState.counter);
                Byte[] sendBytes = Encoding.Unicode.GetBytes(message);
                udpSend.BeginSend(sendBytes, sendBytes.Length, new AsyncCallback(SendCallback), udpSendState);
                sendDone.WaitOne();
            }
            // 发送回调函数
            private void SendCallback(IAsyncResult iar)
            {
                UdpState udpState = iar.AsyncState as UdpState;
                Console.WriteLine("第{0}个请求处理完毕!", udpState.counter);
                Console.WriteLine("number of bytes sent: {0}", udpState.udpClient.EndSend(iar));
                sendDone.Set();
            }
            // 主函数
            public static void Main()
            {
                AsyncUdpSever aus = new AsyncUdpSever();
                Thread t = new Thread(new ThreadStart(aus.ReceiveMsg));
                t.Start();
                Console.Read();
            }
        }
    }
    复制代码

      客户端代码:

    复制代码
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Net;
    using System.Net.Sockets;
    using System.Threading;
    namespace AsyncClient
    {
        // 定义 UdpState类
        public class UdpState
        {
            public UdpClient udpClient = null;
            public IPEndPoint ipEndPoint = null;
            public const int BufferSize = 1024;
            public byte[] buffer = new byte[BufferSize];
            public int counter = 0;
        }
        // 异步UDP类
        public class AsyncUdpClient
        {
            public static bool messageSent = false;
            // Receive a message and write it to the console.
            // 定义端口
            private const int listenPort = 1101;
            private const int remotePort = 1100;
            // 定义节点
            private IPEndPoint localEP = null;
            private IPEndPoint remoteEP = null;
            // 定义UDP发送和接收
            private UdpClient udpReceive = null;
            private UdpClient udpSend = null;
            private UdpState udpSendState = null;
            private UdpState udpReceiveState = null;
            private int counter = 0;
            // 异步状态同步
            private ManualResetEvent sendDone = new ManualResetEvent(false);
            private ManualResetEvent receiveDone = new ManualResetEvent(false);
            // 定义套接字
            //private Socket receiveSocket;
            //private Socket sendSocket;
    
            public AsyncUdpClient()
            {
                // 本机节点
                localEP = new IPEndPoint(IPAddress.Any, listenPort);
                // 远程节点
                remoteEP = new IPEndPoint(Dns.GetHostAddresses(Dns.GetHostName())[0], remotePort);
                // 实例化
                udpReceive = new UdpClient(localEP);
                udpSend = new UdpClient();
    
                // 分别实例化udpSendState、udpReceiveState
                udpSendState = new UdpState();
                udpSendState.ipEndPoint = remoteEP;
                udpSendState.udpClient = udpSend;
    
                udpReceiveState = new UdpState();
                udpReceiveState.ipEndPoint = remoteEP;
                udpReceiveState.udpClient = udpReceive;
    
                //receiveSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
                //receiveSocket.Bind(localEP);
    
                //sendSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
                //sendSocket.Bind(remoteEP);
            }
            // 发送函数
            public void SendMsg()
            {
                udpSend.Connect(remoteEP);
    
                //Thread t = new Thread(new ThreadStart(ReceiveMessages));
                //t.Start();
                Byte[] sendBytes;
                string message;
                while (true)
                {
                    message = "Client" + (counter++).ToString();
                    lock (this)
                    {
                        sendBytes = Encoding.ASCII.GetBytes(message);
                        udpSendState.counter = counter;
                        // 调用发送回调函数
                        udpSend.BeginSend(sendBytes, sendBytes.Length, new AsyncCallback(SendCallback), udpSendState);
                        sendDone.WaitOne();
                        Thread.Sleep(200);
                        ReceiveMessages();
                    }
                }
            }
    
            // 发送回调函数
            public void SendCallback(IAsyncResult iar)
            {
                UdpState udpState = iar.AsyncState as UdpState;
                if (iar.IsCompleted)
                {
                    Console.WriteLine("第{0}个发送完毕!", udpState.counter);
                    Console.WriteLine("number of bytes sent: {0}", udpState.udpClient.EndSend(iar));
                    //if (udpState.counter == 10)
                    //{
                    //    udpState.udpClient.Close();
                    //}
                    sendDone.Set();
                }
            }
    
            // 接收函数
            public void ReceiveMessages()
            {
                lock (this)
                {
                    udpReceive.BeginReceive(new AsyncCallback(ReceiveCallback), udpReceiveState);
                    receiveDone.WaitOne();
                    Thread.Sleep(100);
                }
            }
    
            // 接收回调函数
            public void ReceiveCallback(IAsyncResult iar)
            {
                UdpState udpState = iar.AsyncState as UdpState;
                if (iar.IsCompleted)
                {
                    Byte[] receiveBytes = udpState.udpClient.EndReceive(iar, ref udpReceiveState.ipEndPoint);
                    string receiveString = Encoding.Unicode.GetString(receiveBytes);
                    Console.WriteLine("Received: {0}", receiveString);
                    receiveDone.Set();
                }
            }
    
            // 主函数
            public static void Main()
            {
                AsyncUdpClient auc = new AsyncUdpClient();
                auc.SendMsg();
                Console.Read();
            }
        }
    }
    复制代码

    四、总结

      UDP的异步实现,具有更高的效率,应用实例见博文“基于UDP协议的网络摄像头的设计与实现”。

    出处:http://www.cnblogs.com/sunev/archive/2012/08/15/2604190.html

  • 相关阅读:
    Neutron 理解 (1): Neutron 所实现的虚拟化网络 [How Netruon Virtualizes Network]
    openstack里面的Provider network 和 Tenant network 的区别
    Openstack网络相关概念比较复杂,经常使人混淆,本文进行相关说明。
    OpenStack 网络:Neutron 初探
    openstack 网络架构 nova-network + neutron
    Java 性能测试的四项原则
    微信公众号开发之微信买单
    微信公众号开发之如何使用JSSDK
    微信公众号开发之如何一键导出微信所有用户信息到Excel
    [内核驱动] 链表LIST_ENTRY的操作(转)
  • 原文地址:https://www.cnblogs.com/mq0036/p/7309207.html
Copyright © 2011-2022 走看看