讲udp应用之前,我先简单说一下udp与tcp之间的区别。

 

udp与tcp之间的区别
udp   tcp
容易丢包   保证数据正确性
程序结构简单   程序结构复杂
流模式 数据模式
对系统资源要求少 对系统资源要求多
 无连接   连接 
数据是无序的  数据有序 

 

 

 

 

 

 

 

 

 

                               

 

                                                                                                                 

 

 接下来简单讲一下udp收发包的应用(点对点的应用):

一,发包:

     1,首先创建一个网络端点:    

IPEndPoint ipep = new IPEndPoint(IPAdress.Parse(ip), 9050);

     此类有两个参数:第一个是接收端的IP,第二个是接收端的端口号。

     2,接下来创建一个UdpClient对象:    

UdpClient udpClient=new UdpClient();

    3,准备发送:       

        发送时候有同步和异步两种方式,两种方式都有多种重载方法,下面每个讲其中一种,具体用哪种,看各自的需要。

       a.异步发送:

         方法:BeginSend(...);

         参数:

               BeginSend

                        (

                            byte[] datagram,//要发送的数据字节数组

                            int bytes,//要发送的数据的长度

                           AsyncCallback requestCallback,//发送完成后的回调函数

                           object state//用户自己定义发送完成成后的返回状态,在requestCallback有体现。

                      );

             EndSend

                       (

                              IAsyncResult result//BeginSend返回的IAsyncResult s

                        )

      使用: 

public void SendData(string ip,int port,object data)
{
IPEndPoint ipep = new IPEndPoint(IPAdress.Parse(ip), port);
UdpClient udpClient=new UdpClient();
udpClient.BeginSend(data,data.Length,ipep,SendComplete,new AsyncCallbackArg(ip,udpClient));
}

///<summary>
///发送完成后的回调函数
///</summary>
///<param name="param"></param>
private void sendComplete(IAsyncResult param)
{
AsyncCallbackArg arg=param.AsyncState as AsyncCallbackArg;//param.AsyncState 对应的就是BeginSend的最后一个参数state
using(UdpClient client=(UdpClient)param.AsyncState)
      try

client.EndSend(param);//这句话必须得写,BeginSend()和EndSend()是成对出现的
        catch(Exception ex)
       {
         ....
       }
//自己定义的返回状态参数类型
private struct AsyncCallbackArg
{
private UdpClient udpClient;
private string ipAddress;
public AsyncCallbackArg(string ip,string client)
{
udpClient=client;
ipAddress=ip;
}
}

     b.同步发送:

         方法:Send(...);

         参数:

               Send

              (

                            byte[] datagram,//要发送的数据字节数组

                            int bytes,//要发送的数据的长度

                            IPEndPoint endPoint//接收端的ip和端口对象

               );

      使用: 

 public void SendData(string ip,int port,object data)    
{
IPEndPoint ipep = new IPEndPoint(IPAdress.Parse(ip), port);
UdpClient udpClient=new UdpClient();
udpClient.Send(data,data.Length,ipep);
}

二,收包

     1,首先需要给本地接收端指定一个端口号port。发送端发送数据之前需要传入的是接收端的ip和端口号。 

     2,接下来创建一个UdpClient对象:   

UdpClient udpClient=new UdpClient(port);

    3,准备接收:      

        接收时候同样也有有同步和异步两种方式。

       a.异步接收:

         方法:BeginReceive(...);

         参数:

               BeginReceive

                        (

                            AsyncCallback requestCallback,//接收完后的回调函数                           

                           object state//用户自己定义接收完成成后的返回状态,在requestCallback有体现。

                      );

            EndReceive

                     {

                           IAsyncResult asyncResult,//BeginReceive返回的IAsyncResult

                           ref IPEndPoint remoteEp//获取的发送方的相关信息

                      }

      使用: 

private int m_Port;
private bool m_IsReceive;
private UdpClient m_ReceiveUdpClient;
private Thread m_ReceiveThread;
public void StartReceiveData(int port)
{
  m_IsReceive=true;
m_Port=port;
m_ReceiveThread=new Thread();
m_ReceiveThread.IsBackground=true;
m_ReceiveThreads.start();
}

private void Receive()
{
m_ReceiveUdpClient=new UdpClient(m_Port);
byte[] data;
while(m_IsReceive)
{
if(m_ReceiveUdpClient.Client==null)
{
break;
}
if(m_ReceiveUdpClient.Client.Poll(-1,SelectMode.Selectread))
{
break;
}

try{
m_ReceiveUdpClient.BeginReceive(new AsyncCallBack(ReceiveComplete),m_ReceiveUdpClient);
}catch(Exception ex){ .....}
}
}

private void ReceiveComplete(IAsyncResult param)
{
UDPClient client=param.AsyncState as UDPClient ;//对应的就是BeginSend的最后一个参数state
try

IPEndPoint ipep = new IPEndPoint(IPAdress.Any,m_Port);
byte[] datas=client.EndReceive(param,ref ipep);//接受到的数据

catch(Exception ex) { .... }
}

     b.同步接收:

         方法:Receive(...);

         参数:

               Receive

              (

                         ref  IPEndPoint endPoint////获取的发送方的相关信息s

               );

      使用:

private int m_Port;
public void StartReceiveData(int port)
{
m_Port=port;
m_ReceiveThread=new Thread();
m_ReceiveThread.IsBackground=true;
m_ReceiveThread.start();
}

private void Receive()
{
 m_ReceiveUdpClient=new UdpClient(m_Port);
byte[] data;
while(m_IsReceive)
{
if( m_ReceiveUdpClient.Client==null)
{
break;
}
if( m_ReceiveUdpClient.Client.Poll(-1,SelectMode.Selectread))
{
break;
}
try{
IPEndPoint ip=new IPEndPoint();
data= m_ReceiveUdpClient.Receive(ref ip);

}catch(Exception ex){ .....}
}
}

 停止接收:

private void StopReceive()
{
m_IsReceive=false;
if(m_ReceiveUdpClient!=null)
{
m_ReceiveUdpClient.Close();
}
if(m_ReceiveThread!=null &&m_ReceiveThread.ThreadState==ThreadState.Running)
{
m_ReceiveThread.Abort();
}
}

 

 

posted on 2012-03-28 17:19  写代码的女孩  阅读(3274)  评论(2编辑  收藏  举报