码迷,mamicode.com
首页 > 其他好文 > 详细

Socket之UDP分包组包

时间:2014-06-12 19:39:05      阅读:533      评论:0      收藏:0      [点我收藏+]

标签:style   class   blog   code   java   http   

   一般传输大的文件和信息的时候需要涉及到分包和组包,方法有很多,下面一种是借鉴了别人的思路,供大家参考哈

分包

  1、取出需要传输的文件和字符的长度和大小放入缓存区里面;

  2、设定固定传输的长度,用需要传输的长度除以固定传输的长度都可以得到需要传输的次数;

  3、传输一次字节流中包括(文件名字、文件名字大小、顺序、数据总块数、数据长度、数据总长度)

  4、包组装完成后,都剩下发送;当确定到接收方收到后,在传下一次包;

bubuko.com,布布扣
FileStream m = new FileStream(FullName, FileMode.Open, FileAccess.Read); //FullName得到文件完整路径
                Byte[] BTmp = new byte[m.Length];
                m.Read(BTmp, 0, Convert.ToInt32(m.Length));
                m.Close();
                string fileName = dirs[j].FullName.Replace("\\", "/");
                while (fileName.IndexOf("/") > -1)
                {
                    fileName = fileName.Substring(fileName.IndexOf("/") + 1);
                }
                byte[] fileNameByte = Encoding.UTF8.GetBytes(fileName);
                byte[] fileNameLen = BitConverter.GetBytes(fileNameByte.Length);

                int m_intMessageLength = BTmp.Length;
                int m_intSerial = 0;
                int m_intBlocks = Convert.ToInt32(Math.Ceiling(Convert.ToDouble(m_intMessageLength) / Convert.ToDouble(m_intBlockLength))); //数据分割块数   
                int m_intlastlength = 0;
                //求出最后一块数据长度
                if (m_intMessageLength % m_intBlockLength == 0)
                    m_intlastlength = m_intBlockLength;
                else
                    m_intlastlength = m_intMessageLength - (m_intBlocks - 1) * m_intBlockLength;

                while (m_intSerial < m_intBlocks)
                {
                    try
                    {
                        int m_intLength = 0; //数据长度   
                        if ((m_intSerial + 1) == m_intBlocks)
                            m_intLength = m_intlastlength;
                        else
                            m_intLength = m_intBlockLength;

                        byte[] data = new byte[m_intLength + 20 + fileNameByte.Length];
                        int place = 0;
                        Buffer.BlockCopy(BitConverter.GetBytes(m_intSerial), 0, data, place, 4); //顺序戳   
                        place += 4;
                        Buffer.BlockCopy(BitConverter.GetBytes(m_intBlocks), 0, data, place, 4); //数据总块数    
                        place += 4;
                        Buffer.BlockCopy(BitConverter.GetBytes(m_intLength), 0, data, place, 4); //数据长度   
                        place += 4;
                        Buffer.BlockCopy(BitConverter.GetBytes(BTmp.Length), 0, data, place, 4); //数据总长度   
                        place += 4;
                        ////////////////
                        Buffer.BlockCopy(fileNameLen, 0, data, place, 4); //文件名长度   
                        place += 4;
                        Buffer.BlockCopy(fileNameByte, 0, data, place, fileNameByte.Length); //文件名大小   
                        place += fileNameByte.Length;
                        Array.Copy(BTmp, m_intSerial * 1000, data, place, m_intLength); //复制数据 
                        sersoc.SendTo(data, 0, data.Length, SocketFlags.None, Remot);
                        bool result = sersoc.Poll(1000000, SelectMode.SelectRead);
                        if (result)
                        {
                            byte[] linshi = new byte[1024];
                            int recv = sersoc.ReceiveFrom(linshi, ref Remot);
                            int biaoji = BitConverter.ToInt32(linshi, 0);
                            int i = BitConverter.ToInt32(linshi, 4);//i值为111时表示接到客户端的确认
                            if (biaoji == 999) m_intSerial = i;
                            if (i == 0) break;
                        }

                    } //endtry    
                    catch (System.Exception pe)
                    {
                        Console.WriteLine(pe.ToString());
                    }
bubuko.com,布布扣

组包

  1、收到包后,取出数据总长度和文件名字;

  2、根据顺序写入字节流中,还原成原始包;

bubuko.com,布布扣
 int m_intSerial = 0;
                int m_intBlocks = 0; //数据分割块数   
                int m_intLength = 0; //数据长度   
                int m_intMessageLength = 0;
                int place = 0;
                int recv;
                int biaoji = 999;
                place = 0;
                m_intSerial = BitConverter.ToInt32(bytesF, place);//顺序戳
                place += 4;
                m_intBlocks = BitConverter.ToInt32(bytesF, place);//数据总块数
                place += 4;
                m_intLength = BitConverter.ToInt32(bytesF, place);//数据长度
                place += 4;
                m_intMessageLength = BitConverter.ToInt32(bytesF, place);//数据总长度
                place += 4;
                int count = BitConverter.ToInt32(bytesF, place);//文件名长度
                place += 4;
                string fileName = Encoding.UTF8.GetString(bytesF, place, count);//文件名
                place += count;
                if (m_intSerial == 0)
                { m_intGetCount = 0; data = new byte[m_intMessageLength];  } //申明数据的总长   

                Array.Copy(bytesF, place, data, m_intBlockLength * m_intSerial, m_intLength); //复制数据  
bubuko.com,布布扣

 

Socket之UDP分包组包,布布扣,bubuko.com

Socket之UDP分包组包

标签:style   class   blog   code   java   http   

原文地址:http://www.cnblogs.com/xchit/p/3781788.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!