正确使用BeginReceive/EndReceive

本文关键字:EndReceive BeginReceive | 更新日期: 2023-09-27 18:29:32

从套接字异步接收数据。Net支持对称的BeginReceive/EndReceive调用。基本上,您调用BeginReceive()来开始侦听并确定数据到达时应该调用的回调。在回调中,您可以调用EndReceive()来提取数据并结束异步读取操作。

我正在编写C#/.Net软件来控制一些工业设备。控制面板允许用户设置和初始化设备,一旦初始化,BeginReceive()就被称为开始侦听数据。在回调中,EndReceive()用于提取数据,但我想立即恢复侦听,所以我认为应该在执行EndReceive()之后再次调用BeginReceive()。这是正确的吗?

如果是这样的话,我是否可以在代码的其他地方使用检查或测试来了解BeginReceive()是否已经被调用,这样我就不会在调用EndReceive()之前在同一个套接字上连续调用BeginReceive()两次了?

正确使用BeginReceive/EndReceive

在调用EndReceive()之前避免再次调用BeginReceive()的方法是将对BeginReceive()的调用放入调用EndReceive()的完成回调中。当然,唯一不应该在那里执行的对BeginReceive()的调用是在Socket连接后立即进行的调用。

编辑:

需要明确的是:在任何接收完成之前,允许多次调用BeginReceive()。但当你这样做时,你需要确保你做了必要的内务管理,以确保你以正确的顺序处理数据(即,你以通过BeginReceive()提交缓冲区的相同顺序处理缓冲区)。

因此,上面的答案是关于不必做所有的内务管理,从而使代码更简单。

如果你只在调用EndReceive()的同一个地方对BeginReceive()进行后续调用,那么保持秩序是很琐碎的。不过,请注意,您仍然需要正确地执行此操作:确保始终以正确的顺序接收缓冲区的最简单方法是,在调用EndReceive()(但仍然使用相同的方法)之后的之前,不要再次调用BeginReceive()

是的,您需要在接收完数据后调用BeginReceive,以便在数据可用时获得更多信息。

在不调用BeginReceive两次的情况下,由您来处理Socket的状态。有一些属性可以让您知道数据是否可用,但没有任何属性可以告诉您是否已经在等待接收数据。

Socket的大多数实现最终都是另一个具有此逻辑的包装器类,因此如果第二次调用BeginReceive,就会忽略它。Socket类有时有点痛苦,因为您不能在不关闭的情况下取消BeginReceive