我想知道是否可以为UdpClient接收方法设置超时值。我可以在C#中设置UdpClient的超时时间吗?
我想使用块模式,但因为有时udp会丢失数据包,我的程序udpClient.receive将永远挂在那里。
任何好主意我怎么能管理呢?
我想知道是否可以为UdpClient接收方法设置超时值。我可以在C#中设置UdpClient的超时时间吗?
我想使用块模式,但因为有时udp会丢失数据包,我的程序udpClient.receive将永远挂在那里。
任何好主意我怎么能管理呢?
菲利普所指的是嵌套在UdpClient
包含的套接字中(UdpClient.Client.ReceiveTimeout
)。
您也可以使用异步方法来做到这一点,但手动挡执行:
var timeToWait = TimeSpan.FromSeconds(10);
var udpClient = new UdpClient(portNumber);
var asyncResult = udpClient.BeginReceive(null, null);
asyncResult.AsyncWaitHandle.WaitOne(timeToWait);
if (asyncResult.IsCompleted)
{
try
{
IPEndPoint remoteEP = null;
byte[] receivedData = udpClient.EndReceive(asyncResult, ref remoteEP);
// EndReceive worked and we have received data and remote endpoint
}
catch (Exception ex)
{
// EndReceive failed and we ended up here
}
}
else
{
// The operation wasn't completed before the timeout and we're off the hook
}
您可以使用ReceiveTimeout属性。
有一个SendTimeout
,并且可以在UdpClient
的Socket
使用ReceiveTimeout
属性。
这里是5秒超时的例子:
var udpClient = new UdpClient();
udpClient.Client.SendTimeout = 5000;
udpClient.Client.ReceiveTimeout = 5000;
...
这只适用于您正在进行同步发送/接收。对于异步调用,你可以使用'Task.Delay'来创建你自己的超时时间,例如'Task.WhenAny(udpClient.ReceiveAsync(),Task.Delay(5000))'; – 2017-05-31 20:16:23
当然好!我怎么错过这个简单的解决方案!感谢您的评论AJ! – 2017-11-10 10:57:59
实际上,看来UdpClient
坏,当涉及到超时。我试图写一个服务器的线程只包含一个接收到的数据并将其添加到队列中。多年来,我通过TCP完成了这类事情。期望的是,循环在接收处阻塞,直到来自请求者的消息为止。但是,尽管将超时设置为无穷大:
_server.Client.ReceiveTimeout = 0; //block waiting for connections
_server.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReceiveTimeout, 0);
大约3分钟后套接字超时。
我发现的唯一解决方法是捕捉超时异常并继续循环。这隐藏了微软的错误,但未能回答为什么会发生这种根本性问题。
我想有一个200000毫秒左右的内部超时? – 2013-04-22 22:05:44
,你可以这样做:
udpClient.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReceiveTimeout, 5000);
感谢您的答复。 – Jack 2010-02-17 14:45:29
这是很久以前的!现在看起来不错。 WaitOne还会返回一个结果,您可以使用它来确定它是否超时。 – weston 2014-07-09 21:50:02