当前位置: 首页 > 知识库问答 >
问题:

如何在.NET中的套接字编程(TCP/IP)中收集接收到的缓冲区?

柳韬
2023-03-14

我使用服务器-客户机模型与使用套接字编程的硬件板进行通信。

我使用“NetworkStream”类的“read()”方法从板上接收数据,该方法读取指定最大大小的缓冲区,并返回缓冲区中有效数据的长度。我已经考虑了一个足够大的数字缓冲区的最大大小。

该板每100ms发送一组消息。每条消息包含一个2字节的常量报头和一个作为报头字节之后的数据的可变字节数。

共有1个答案

单于扬
2023-03-14

您需要在您的使用者DFA和套接字客户端之间添加一个额外的缓冲区组件。

每当数据可以从NetworkStream中获得时,buffer组件就会读取它,并将它追加到自己的专用缓冲区中,增加一个“可用字节”计数器。缓冲区组件至少需要向其用户公开以下功能:

  1. BytesAvailable属性--返回计数器的值
  2. peekbytes(int count)方法--如果缓冲区的第一个count字节至少可用,则返回该字节,并且不修改计数器或缓冲区
  3. 一个readbytes(int count)方法--如上所述,但它会将计数器递减count并移除从缓冲区读取的字节,以便后续的peekbytes调用将永远不会再读取它们

请记住,您不需要能够为任意高的count参数提供服务;如果您能够为count提供与它在任何时候都可能接收到的最长消息一样长的服务,这就足够了。

显然,缓冲区组件需要保留某种数据结构,这种结构允许某种类型的“环绕”;您可能希望查看循环(环形)缓冲区实现,或者您可以只使用两个大小为n的固定缓冲区,其中n是最长消息的长度,并在它们满时从一个切换到另一个。您应该小心,以便在缓冲区已满时停止从NetworkStream中拉入数据,并且只有在DFA调用ReadBytes以释放一些缓冲区空间后才继续拉入数据。

每当您的DFA需要读取数据时,它会首先询问您的缓冲级已经积累了多少数据,然后相应地进行。它看起来像这样:

if BytesAvailable < 2
    return; // no header to read, cannot do anything

// peek at the header -- do not remove it from the buffer!
header = PeekBytes(2);

// calculate the full message length based on the header
// if this is not possible from just the header, you might want to do this
// iteratively, or you might want to change the header so that it is possible
length = X; 

if BytesAvailable < X
    return; // no full message to read, cannot continue

header = ReadBytes(2); // to remove it from the buffer
message = ReadBytes(X); // remove the whole message as well
 类似资料:
  • 问题内容: 我有一个内存泄漏,我已经将其隔离到错误配置的直接字节缓冲区。 GC收集包含这些缓冲区但不处理缓冲区本身的对象。如果实例化包含缓冲区的瞬态对象足够多,则会得到以下令人鼓舞的消息: 我一直在寻找这个问题,显然 和 不工作。 问题答案: 我怀疑您的应用程序某处有对ByteBuffer实例的引用,这阻止了它被垃圾回收。 直接ByteBuffer的缓冲内存是在普通堆之外分​​配的(以便GC不会移

  • 我使用Android应用程序通过TCP套接字与同一局域网上的PC java应用程序进行通信、发送和接收消息。下面是我在android中使用的Asynctask的代码,用于发送消息并从PC接收回复: } 我在onPostExcecute中的祝酒词中显示PC的回复。 Android通过BufferedWriter发送消息,而PC上的java应用程序在BufferedReader中接收消息。 PC在收到

  • 我正在编写一个c#tcp套接字服务器,它将从c套接字应用程序接收数据。现在,除了我的c#接收线程中的循环中断逻辑外,其他一切都正常工作。为了更好地解释,我在下面展示了一段代码片段。 下面是连续接收数据的线程函数 为了更好地了解情况,我在我的通讯协议下面写了一些东西。 客户端发起连接。发送数据集 服务器接收,处理,发送ack 客户端处于停止模式,直到它收到来自服务器的ack,但没有关闭套接字 这一次

  • 如果客户端侦听套接字,则在http://socketplaceonnet.com例如,它如何知道有新内容?我假设服务器无法直接向客户端发送数据,因为客户端可能位于路由器后面,没有端口转发,因此无法直接连接。客户端可能是一部移动电话,可以更改其IP地址。我理解,要让客户端成为侦听器,服务器不需要知道客户端的IP。 非常感谢。

  • 问题内容: 我要通过TCP / IP编写程序,我应该通过客户端或服务器发送对象,当我想发送或接收字符串但尝试读取对象时,它是正确的: 我收到一个例外: 它指的是这一行: 这是我的服务器代码: 客户端代码: 谁能解释我发生了什么,这个例外是什么,为什么我收到这个例外? 问题答案: 只是摆脱发送和接收布尔值的麻烦。这是多余的。如果在创建连接时遇到问题,则不会创建套接字:而是抛出异常。您会将所有内容与同

  • 我有一个很奇怪的问题快把我逼疯了。 我有一个Ruby服务器和一个Flash客户端(动作脚本3)。这是一个多人游戏。 问题是,一切都在完美地工作,然后,突然,一个随机的球员停止接收数据。当服务器因为不活动而关闭连接时,大约20-60秒后,客户端接收到所有缓冲的数据。 null 我不认为这是一个操作系统/网络问题,因为我已经从一个位于西班牙的VPS换到了位于爱尔兰的亚马逊EC2,问题仍然存在。 我觉得