Python论坛  - 讨论区

标题:[python-chinese] 请教关于socket.recv()的问题

2007年02月07日 星期三 11:25

du.raymond.dl在gmail.com du.raymond.dl在gmail.com
星期三 二月 7 11:25:34 HKT 2007

Çé¿ö£º
    ·þÎñ¶ËÁ¬Ðø·¢ËÍ2¸öÒÔÉϵİüÖÁ¿Í»§¶Ë£¬µ±¿Í»§¶ËʹÓÃrecv·½·¨Ê±»á½«¼¸¸ö°ü¶¼Á¬ÔÚÒ»Æð£¬ÎÞ·¨°´¸ñʽÅжÏÁË

ÎÊÌ⣺
    socketµÄrecv·½·¨ÊÇÊÕµ½Ò»¸ö°ü¾ÍÈ¥´¦Àí£¬»¹ÊÇÊÕÂúbuffÔÙÈ¥´¦Àí?
    Èç¹ûÊÇÊÕÂúbuffÈ¥´¦ÀíµÄ»°£¬ÔÚÕ³Á¬µÄ2¸ö°üûÓбê×¼¸ñʽµÄÇé¿öÏ£¬ÓÐʲô°ì·¨È¥°ÑËûÃÇ·Ö¿ª 
-------------- 下一部分 --------------
Ò»¸öHTML¸½¼þ±»ÒƳý...
URL: http://python.cn/pipermail/python-chinese/attachments/20070207/20cbc7a6/attachment.html 

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 11:41

Yingbo Qiu qiuyingbo在gmail.com
星期三 二月 7 11:41:43 HKT 2007

我觉得数据包应该有自己的格式.

而且对于你的发送端来说,你怎么就那么确定你是发了2个包呢?是用 ethereal 听出来的么?

应用程序调用两次 send/write ,未必一定会发 2 个包,这要看协议栈的实现啊

同理,协议栈收到 2 个以太包,有可能全部放在 buffer 里面等待操作系统调用 read/recv。

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 12:27

vcc vcc在163.com
星期三 二月 7 12:27:51 HKT 2007

你理解错TCP/IP包的含义了,包只是传输层的,在你的应用层,你还得定义自己的数据协议结构,通常有个头部,例如最简单就是发送的数据长度,这样你接收端就可以分包了。可以参考一下别的协议,例如http等。
  ----- Original Message ----- 
  From: du.raymond.dl at gmail.com 
  To: python-chinese at lists.python.cn 
  Sent: Wednesday, February 07, 2007 11:25 AM
  Subject: [python-chinese] 请教关于socket.recv()的问题


  情况:
      服务端连续发送2个以上的包至客户端,当客户端使用recv方法时会将几个包都连在一起,无法按格式判断了

  问题:
      socket的recv方法是收到一个包就去处理,还是收满buff再去处理?
      如果是收满buff去处理的话,在粘连的2个包没有标准格式的情况下,有什么办法去把他们分开 


------------------------------------------------------------------------------


  _______________________________________________
  python-chinese
  Post: send python-chinese at lists.python.cn
  Subscribe: send subscribe to python-chinese-request at lists.python.cn
  Unsubscribe: send unsubscribe to  python-chinese-request at lists.python.cn
  Detail Info: http://python.cn/mailman/listinfo/python-chinese
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://python.cn/pipermail/python-chinese/attachments/20070207/ab445608/attachment.htm 

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 12:47

du.raymond.dl du.raymond.dl在gmail.com
星期三 二月 7 12:47:49 HKT 2007

vcc 写道:
> 你理解错TCP/IP包的含义了,包只是传输层的,在你的应用层,你还得定义自己
> 的数据协议结构,通常有个头部,例如最简单就是发送的数据长度,这样你接收
> 端就可以分包了。可以参考一下别的协议,例如http等。
>
>     ----- Original Message -----
>     *From:* du.raymond.dl在gmail.com du.raymond.dl在gmail.com>
>     *To:* python-chinese在lists.python.cn
>     python-chinese在lists.python.cn>
>     *Sent:* Wednesday, February 07, 2007 11:25 AM
>     *Subject:* [python-chinese] 请教关于socket.recv()的问题
>
>     情况:
>     服务端连续发送2个以上的包至客户端,当客户端使用recv方法时会将几个
>     包都连在一起,无法按格式判断了
>     问题:
>     socket的recv方法是收到一个包就去处理,还是收满buff再去处理?
>     如果是收满buff去处理的话,在粘连的2个包没有标准格式的情况下,有什
>     么办法去把他们分开
>
>     ------------------------------------------------------------------------
>     _______________________________________________
>     python-chinese
>     Post: send python-chinese在lists.python.cn
>     python-chinese在lists.python.cn>
>     Subscribe: send subscribe to
>     python-chinese-request在lists.python.cn
>     python-chinese-request在lists.python.cn>
>     Unsubscribe: send unsubscribe to
>     python-chinese-request在lists.python.cn
>     Detail Info: http://python.cn/mailman/listinfo/python-chinese
>
> ------------------------------------------------------------------------
>
> _______________________________________________
> python-chinese
> Post: send python-chinese在lists.python.cn
> Subscribe: send subscribe to python-chinese-request在lists.python.cn
> Unsubscribe: send unsubscribe to  python-chinese-request在lists.python.cn
> Detail Info: http://python.cn/mailman/listinfo/python-chinese
如果流程仅仅是,
1 server --> client
2 client --> server
...
那client在socket.recv收到第一个包以后开始处理,而不是无止境的等待buff的充满


如果流程是
1 server --> client
2 server --> client
3 client --> server
...
那client的socket.recv返回值是将1,2两个包的内容连接在一起

由这2种情况分析,可能是socket.recv的方法是在一段时间内(时间段可能是很小
很小的)将收到的东西传回应用层。

你的意思是通过确定包数据长度来设置recv buff, 但是现在无法确定的知道对方
传来的结构,因此更无法知道准确的数据长度





[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 13:16

vcc vcc在163.com
星期三 二月 7 13:16:18 HKT 2007

> 如果流程是
> 1 server --> client
> 2 server --> client
> 3 client --> server
> ...
> 那client的socket.recv返回值是将1,2两个包的内容连接在一起
> 
> 由这2种情况分析,可能是socket.recv的方法是在一段时间内(时间段可能是很小
> 很小的)将收到的东西传回应用层。
> 
> 你的意思是通过确定包数据长度来设置recv buff, 但是现在无法确定的知道对方
> 传来的结构,因此更无法知道准确的数据长度

给一段伪代码看看应该就比较清楚了:
1 server --> client, 假设数据长度是LEN1
先发送长度:send(LEN1)
再发送数据:  send(DATA1)
> 2 server --> client
先发送长度:send(LEN2)
再发送数据:  send(DATA2)
> 3 client --> server
同理

客户端接受先接收长度,假设是用4个字节的长度,
LEN=recv(4)
DATA=recv(LEN)

这样应该是比较清楚了。

vcc
_

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 13:30

du.raymond.dl du.raymond.dl在gmail.com
星期三 二月 7 13:30:11 HKT 2007

这样在流程上的确很清晰,但是

实际流程是
1. client --> server
    #msg: request
2. server --> client
    #msg: ACK
3. server --> client
    #msg:data
现在的情况
    socket.send("request")
    print socket.recv(64)
    >>>ACKdata

你的说法
client:
    socket.send("request")
    LEN = socket.recv(4)
    socket.recv(LEN)
    #长度server是不会传给你的吧

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 13:52

vcc vcc在163.com
星期三 二月 7 13:52:47 HKT 2007

> 现在的情况
>    socket.send("request")
>    print socket.recv(64)
>    >>>ACKdata
> 
> 你的说法
> client:
>    socket.send("request")
>    LEN = socket.recv(4)
>    socket.recv(LEN)
>    #长度server是不会传给你的吧

似乎有一个ACK的头,可以用这个来分包。
不清楚你的应用是怎样的,一般数据都有格式的,按格式分包即可。服务器不是你写的?服务器也可分长连接,短连接,短连接可以不定义数据格式,服务器发完一个就断开连接,这样就不会混淆。

vcc
_

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 14:04

xxmplus xxmplus在gmail.com
星期三 二月 7 14:04:23 HKT 2007

tcp是流, 你对收进来的数据什么都不知道, 你怎么分啊
ack是tcp层的, 你的数据在tcp之上, ack对你一点意义都没有

On 2/7/07, vcc <vcc at 163.com> wrote:
> > 现在的情况
> >    socket.send("request")
> >    print socket.recv(64)
> >    >>>ACKdata
> >
> > 你的说法
> > client:
> >    socket.send("request")
> >    LEN = socket.recv(4)
> >    socket.recv(LEN)
> >    #长度server是不会传给你的吧
>
> 似乎有一个ACK的头,可以用这个来分包。
> 不清楚你的应用是怎样的,一般数据都有格式的,按格式分包即可。服务器不是你写的?服务器也可分长连接,短连接,短连接可以不定义数据格式,服务器发完一个就断开连接,这样就不会混淆。
>
> vcc
> _
> _______________________________________________
> python-chinese
> Post: send python-chinese at lists.python.cn
> Subscribe: send subscribe to python-chinese-request at lists.python.cn
> Unsubscribe: send unsubscribe to  python-chinese-request at lists.python.cn
> Detail Info: http://python.cn/mailman/listinfo/python-chinese


-- 
Any complex technology which doesn't come with documentation must be the best
available.

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 14:15

du.raymond.dl du.raymond.dl在gmail.com
星期三 二月 7 14:15:50 HKT 2007

vcc 写道:
>> 现在的情况
>>    socket.send("request")
>>    print socket.recv(64)
>>    >>>ACKdata
>>
>> 你的说法
>> client:
>>    socket.send("request")
>>    LEN = socket.recv(4)
>>    socket.recv(LEN)
>>    #长度server是不会传给你的吧
>>     
>
> 似乎有一个ACK的头,可以用这个来分包。
> 不清楚你的应用是怎样的,一般数据都有格式的,按格式分包即可。服务器不是你写的?服务器也可分长连接,短连接,短连接可以不定义数据格式,服务器发完一个就断开连接,这样就不会混淆。
>
> vcc
> _
> _______________________________________________
> python-chinese
> Post: send python-chinese在lists.python.cn
> Subscribe: send subscribe to python-chinese-request在lists.python.cn
> Unsubscribe: send unsubscribe to  python-chinese-request在lists.python.cn
> Detail Info: http://python.cn/mailman/listinfo/python-chinese
我请教了我们公司C++的人,现在理解了你的LEN的意思,那是在打这个ip包的时候 
将数据的长度在包头作定义。tcp/ip都看忘记了。:(

如果这种办法的话,要分开这2个包就要取IP头里的数据长度了,这个不知道 
python里面有什么方法可以做到的

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

2007年02月07日 星期三 18:29

麦田守望者 qcxhome在gmail.com
星期三 二月 7 18:29:54 HKT 2007

On 2/7/07, du.raymond.dl <du.raymond.dl at gmail.com> wrote:
> vcc 写道:
> >> 现在的情况
> >>    socket.send("request")
> >>    print socket.recv(64)
> >>    >>>ACKdata
> >>
> >> 你的说法
> >> client:
> >>    socket.send("request")
> >>    LEN = socket.recv(4)
> >>    socket.recv(LEN)
> >>    #长度server是不会传给你的吧
> >>
> >
> > 似乎有一个ACK的头,可以用这个来分包。
> > 不清楚你的应用是怎样的,一般数据都有格式的,按格式分包即可。服务器不是你写的?服务器也可分长连接,短连接,短连接可以不定义数据格式,服务器发完一个就断开连接,这样就不会混淆。
> >
> > vcc
> > _
> > _______________________________________________
> > python-chinese
> > Post: send python-chinese at lists.python.cn
> > Subscribe: send subscribe to python-chinese-request at lists.python.cn
> > Unsubscribe: send unsubscribe to  python-chinese-request at lists.python.cn
> > Detail Info: http://python.cn/mailman/listinfo/python-chinese
> 我请教了我们公司C++的人,现在理解了你的LEN的意思,那是在打这个ip包的时候
> 将数据的长度在包头作定义。tcp/ip都看忘记了。:(
>
> 如果这种办法的话,要分开这2个包就要取IP头里的数据长度了,这个不知道
> python里面有什么方法可以做到的
> _______________________________________________
> python-chinese
> Post: send python-chinese at lists.python.cn
> Subscribe: send subscribe to python-chinese-request at lists.python.cn
> Unsubscribe: send unsubscribe to  python-chinese-request at lists.python.cn
> Detail Info: http://python.cn/mailman/listinfo/python-chinese

哪用这么麻烦,你说的这些留给socket去做。你现在需要关心的是recv方法的使用,建议仔细看看文档,同时理解下协议的含义。

-- 
GoogleTalk: qcxhome at gmail.com
MSN: qcxhome at hotmail.com
My Space: tkdchen.spaces.live.com
BOINC: boinc.berkeley.edu
中国分布式计算总站: www.equn.com

[导入自Mailman归档:http://www.zeuux.org/pipermail/zeuux-python]

如下红色区域有误,请重新填写。

    你的回复:

    请 登录 后回复。还没有在Zeuux哲思注册吗?现在 注册 !

    Zeuux © 2025

    京ICP备05028076号