找回密码
 用户注册

QQ登录

只需一步,快速开始

查看: 3300|回复: 5

proactor服务器端数据打包问题

[复制链接]
发表于 2009-7-7 10:42:39 | 显示全部楼层 |阅读模式
正如几位高手所说,数据必须要打包发送,自己定一个协议,以解包和打包
现在这个过程中遇到如下难题:先贴代码上来,再慢慢看问题:

//发送函数,参数中容器fcls和objs中装的就是要传送的数据,是需要发送的数据
//设计为先发送fcls再发送objs
//初步决定4KB为一个包发送,所以涉及到打包问题,以fcls为例每个fcls前加一个包头,其中有flag和数据长度

int CommunicationServer::sendData(std::vector<FeatureClassPtr> &fcls,std::vector<Feature*> &objs)
{
//先发送fcls ,每个数据段前加一个包头,格式为:flag(f/o) + length
char packHead[5] = "f";


for(std::vector<FeatureClassPtr>::iterator i = fcls.begin();i != fcls.end();++i)
{
//....
//得到flcs中的数据buf
//....

  size_t *pb = (size_t *)(packHead+1);   //写好包头中的length
  *pb = buf->size();

  ACE_Message_Block *mb;
  ACE_NEW_RETURN(mb, ACE_Message_Block(4096), -1);

   if (-1 == mb->copy((const char *)packHead,5))  //写包头
   {
    size_t ncoun_left = mb->space();
    mb->copy((const char *)packHead,ncoun_left);
    initWriteStream(*mb,4096);
   }
   else
   {
    if (-1 == mb->copy((const char*)buf->begin(),buf->size())) //写具体数据
    {
     size_t ncount_left = mb->space();
     mb->copy((const char *)buf->begin(),ncount_left);
     initWriteStream(*mb,4096);
    }
   }

//上述代码中有很大问题,其一,把mb声明放循环里面,每循环一次,申请一个mb,显然不能达到打包的效果
//其二,把mb声明放循环外面,那当打好一个包后,又不能把它release掉,还是不能打包
//其三,先计算所有要发送的数据总长,要打包多少,然后定义一个mb 数组,一个一个用掉。。。方案看似可行,但过于复杂

请问高手,如何解决这种Proactor 的打包问题。。。。
发表于 2009-7-7 17:02:12 | 显示全部楼层
你没有理解ACE_Message_Block的特点。此类是ACE系统的血液,它靠引用计数管理。
你的这种需求很常见的。如果不是受限的系统,图简单的话,完全可以用小的block存储,再内部cont或者link一下。
一起处理的。
非常灵活。
发表于 2009-7-8 14:29:09 | 显示全部楼层
正如几位高手所说,数据必须要打包发送,自己定一个协议,以解包和打包

请问楼主,你说发送数据必须要打包,能说下理由么?只知其然不知其所以然是不够的。

个人观点:如果只是为了发数据,不需要打包,也不需要用message block。ACE_Message_Block是很强大,但是比简单缓冲区的使用和管理要复杂得多。它有自己的适用场合,不要为了用而用。
 楼主| 发表于 2009-7-8 16:25:39 | 显示全部楼层

回复 #3 wishel 的帖子

我是异步写的,它的接口ACE_Asynch_write_stream( ACE_Message_Block * ,size_t )参数就是 message block啊,那该怎么用简单缓冲区?
 楼主| 发表于 2009-7-8 16:27:41 | 显示全部楼层
我觉得这不关 message block 的事,发消息不打包,随便一个大一个小的发吗?那接收方怎么知道下一次发多大?
有人说先发数据长度过去,再发数据,可是我是异步发送的啊,那万一顺序乱了,接收方怎么接?
发表于 2009-7-8 16:55:53 | 显示全部楼层
本来就是ACE_Message_Block那当然不必再转成简单缓冲区。
不打包一样可以发,是否打包看具体需求,比如你发个文件,有必要拆包打包么?eof就是fin,收到就证明完了,大小都不需要事先通知。
异步发送的问题,只要你保证发送时的调用顺序,完成顺序就能保证(同一handle)。接收方收到的也是顺序的。

我前面的评论是针对这句话“数据必须要打包发送,自己定一个协议,以解包和打包”。
不能太绝对,不同应用场景适合不同的发送方式。
您需要登录后才可以回帖 登录 | 用户注册

本版积分规则

Archiver|手机版|小黑屋|ACE Developer ( 京ICP备06055248号 )

GMT+8, 2024-12-23 18:04 , Processed in 0.021095 second(s), 5 queries , Redis On.

Powered by Discuz! X3.5

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表