C# 我需要调用TcpListener.Stop()吗?
我将此代码放在一个单独的线程(任务)中,该线程在应用程序启动时首先运行,在应用程序关闭之前不应结束:C# 我需要调用TcpListener.Stop()吗?,c#,multithreading,C#,Multithreading,我将此代码放在一个单独的线程(任务)中,该线程在应用程序启动时首先运行,在应用程序关闭之前不应结束: TcpListener tcpListener = new TcpListener(IPAddress.Any, port); tcpListener.Start(); while (true) { TcpClient client = tcpListener.AcceptTcpClient(); Task.Factory.StartNew(HandleClientComm
TcpListener tcpListener = new TcpListener(IPAddress.Any, port);
tcpListener.Start();
while (true)
{
TcpClient client = tcpListener.AcceptTcpClient();
Task.Factory.StartNew(HandleClientCommunication, client);
}
在这种情况下,是否需要调用tcpListener.Stop()
?这个线程在应用程序的整个过程中都会运行,如果我真的需要调用它,我会在哪里调用它?侦听器是此线程的本地。我会使用while(appRunning)
循环而不是while(true)
循环,并在FormClosing事件中将appRunning设置为false吗?然后在while循环之后,我可以调用tcpListener.Stop()
但是,是否有必要调用
TcpListener.Stop()
public class Listener
{
private readonly TcpListener m_Listener = new TcpListener(IPAddress.Any, IPEndPoint.MinPort);
private CancellationTokenSource m_Cts;
private Thread m_Thread;
private readonly object m_SyncObject = new object();
public void Start()
{
lock (m_SyncObject){
if (m_Thread == null || !m_Thread.IsAlive){
m_Cts = new CancellationTokenSource();
m_Thread = new Thread(() => Listen(m_Cts.Token))
{
IsBackground = true
};
m_Thread.Start();
}
}
}
public void Stop()
{
lock (m_SyncObject){
m_Cts.Cancel();
m_Listener.Stop();
}
}
private void Listen(CancellationToken token)
{
m_Listener.Start();
while (!token.IsCancellationRequested)
{
try{
var socket = m_Listener.AcceptSocket();
//do something with socket
}
catch (SocketException){
}
}
}
}
使用TcpListener.Pending()
的方法不太好,因为您必须使用Thread.Sleep(毫秒)
或类似的方法-在客户端接受(毫秒睡眠)之间会有一些延迟,这很糟糕。可能重复有几个原因让开发人员觉得有必要在.NET应用程序关闭时明确停止线程-当他们看到其他开发人员这样做时,因为这感觉“干净”,或者因为他们的工作线程直接读/写表单/组件/应用程序关闭时释放的任何数据丢失,(因此产生AV/SEGFULT等)。您的侦听器线程本身似乎不需要执行任何需要显式停止的操作,因此当主线程关闭并调用ExitProcess()时,让操作系统执行此操作@Jim:如果您想提供一些示例代码,说明如何在这种情况下实现取消令牌以解决此问题,我很乐意接受答案:)@Jim Mischel-如果OP对其进行了重大更改,那么,是的,可能需要在其他应用程序中停止。也许另一个应用程序需要在应用程序关闭前停止,但这是另一个应用程序。另外,可能我误解了取消机制——当请求取消时,阻塞AcceptCpcClient()调用内部会发生什么?是否立即返回错误或异常?我想我应该查找或尝试一下。好的,我能看到的使用取消机制显式停止此线程的唯一方法是注册一个取消回调,通过在“localhost”上打开客户端连接(假设绑定集中有127.0.0.1)来取消对AcceptCpcClient()调用的阻止,从而导致AcceptCpcClient()使用实际连接返回。然后,侦听器可以检查token.IsCancellationRequested,从而意识到它必须终止。这比让操作系统清理要混乱得多,除非绝对必要,否则我不会靠近它。操作系统非常非常擅长停止线程:)感谢你制作的漂亮类,它对我正在处理的项目非常有用。此解决方案的问题是AcceptSocket方法被阻塞。因此,在侦听线程等待传入连接时,您无法正常停止它。