我有以下代码,如果在2秒内未完成,我想中止一个线程。 你可以从第一个代码看到我在while循环中创建一个新的myThread evertyime并且不要中止它。好吧,我不希望它像这样,但如果我在循环外部使用myThread并使用abort()函数作为第二个代码。中止会有错误。
while (true)
{
try
{
m_socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);//reset up socket
myThread = new System.Threading.Thread(new System.Threading.ThreadStart(socket_connect));
myThread.Start();
if (!myThread.Join(2000))
{
throw new SocketException(SocketError.AccessDenied);
}
}
catch (Exception ex)
{
m_socket.Close();
}
}
}
private static void socket_connect()
{
m_socket.Connect(remoteEndPoint);//Connect to remote device
}
我最初尝试使用以下代码,但是它提供了threadabortexceptions。
myThread = new System.Threading.Thread(new System.Threading.ThreadStart(socket_connect));
while (true)
{ try
{
m_socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);//reset up socket
myThread.Start();
if (!myThread.Join(2000))
{
myThread.Abort();
throw new SocketException(SocketError.AccessDenied);
}
}
catch (Exception ex)
{
m_socket.Close();
}
}
}
private static void socket_connect()
{
m_socket.Connect(remoteEndPoint);//Connect to remote device
}
我知道abort()不是一个好主意所以我转而让线程留下来让C#(。Net?我不知道是谁真的那么做)处理垃圾收集。任何人都可以判断这是不是一个好主意,因为这个程序将在一个没有大量内存来保存一串线程的板上运行。并且有人可以告诉我C#中的垃圾收集是如何完成的?例如线程。
另一件需要提及的是我没有Task类或socket.beginconnect()方法,我猜它是因为我正在构建一个程序,它将在一块小板上运行,而不是一台PC。董事会是netduido plus,我正在netduino plus平台上构建我的项目。
答案 0 :(得分:1)
我有以下代码,如果在2秒内未完成,我想中止一个帖子。
阅读代码,看起来您实际上想要在两秒钟内尝试将套接字连接到资源。如果超过两秒钟,您想继续前进。
我主要是在this answer中复制代码,我相信这大致是你应该为实现目标所做的,而不是启动线程并中止它:
Socket socket = new Socket(AddressFamily.InterNetwork,
SocketType.Stream,
ProtocolType.Tcp);
// Connect using a timeout (2 seconds)
IAsyncResult result = socket.BeginConnect( sIP, iPort, null, null );
bool success = result.AsyncWaitHandle.WaitOne( 2000, true );
if ( !success )
{
// NOTE, MUST CLOSE THE SOCKET
socket.Close();
throw new ApplicationException("Failed to connect server.");
}
// Success
//...
答案 1 :(得分:-1)
[编辑:大量的copypasta在解开/间隔时失败]
哦,请使用Task
库,这样可以更轻松地处理这些情况:
(LINQPad-friendly blob)
void Main()
{
var canceller = new CancellationTokenSource();
var task = Task.Factory.StartNew(() => DoStuff(canceller.Token), canceller.Token);
if(!task.Wait(2000, canceller.Token))
{
canceller.Cancel();
task.Wait(2);
}
sw.Elapsed.Dump();
}
private Stopwatch sw;
private void DoStuff(CancellationToken token)
{
try
{
sw = Stopwatch.StartNew();
while(!token.IsCancellationRequested)
{
}
}
// no catch - rethrown exceptions must be checked on Task
finally
{
sw.Stop();
}
}
或者,您可以使用一些“退出标志”条件 - 您的线程启动器和您的线程转换器都可以看到/更改的bool,并在while
条件下使用它。