【发布时间】:2011-04-07 13:10:45
【问题描述】:
对于如何正确实现 TcpListner 和 TcpClient int .NET 的异步方法,我有点不知所措。我已经阅读了很多关于hear 的帖子,我相信我有代码可以在服务器上接受新客户端。下面是接受新连接的代码:
Public Sub Start()
m_oListener = New TcpListener(m_oIpAddress, m_iPort)
m_oListener.Start()
m_oListener.BeginAcceptTcpClient(New AsyncCallback(AddressOf OnAcceptClient), m_oListener)
End Sub
Public Sub OnAcceptClient(ByVal ar As IAsyncResult)
Dim listener As TcpListener = CType(ar.AsyncState, TcpListener)
Dim client As TcpClient = listener.EndAcceptTcpClient(ar)
If listener.Server.IsBound Then
ThreadPool.QueueUserWorkItem(New WaitCallback(AddressOf OnHandleClient), client)
listener.BeginAcceptTcpClient(New AsyncCallback(AddressOf OnAcceptClient), listener)
End If
End Sub
我不确定的是,一旦建立连接,客户端该怎么做。据我所知,通常人们会为每个连接的客户端创建一个新线程,以防止 IO 读取阻塞应用程序。
我的应用程序将在任何给定时间连接多达 100 个客户端。如果我为每个客户分拆一个新线程,那么我将拥有 100 个左右的线程。那是对的吗?我想我只是缺少 .NET 框架中的异步方法。
我看到的大多数示例都让服务器接受连接,读入一条短消息(例如“hello server”),然后关闭客户端并关闭服务器。这并不能帮助我理解在很长一段时间内保持大量活跃客户的正确方法。
提前感谢您的帮助。
【问题讨论】:
-
好吧,我现在看到我可能应该使用 TcpClient.GetStream().BeginRead() 从流中异步读取数据。如果我使用 BeginRead(),是否需要使用 ThreadPool.QueueUserWorkItem?我看到的几个示例使用了线程轮询,但这里似乎不需要它,因为我想当我使用 BeginXXX 和 EndXXX 方法时,.NET 框架正在使用线程池。
-
使用
BeginRead()方法已经将你放入线程池,所以你已经准备好了。 -
太好了,感谢您的快速回复。
标签: .net multithreading sockets tcp tcplistener