C#: 一个方法执行超时 timeout 检查的实现

我们经常有这样的需求:如果一个方法的执行,超过了一个设定时间(timeout)就需要立即返回不再继续,这里我利用 C# 异步委托的 AsyncWaitHandle 来尽量简便的实现这一需求。

具体实现如下。注意,这里需要被调用的方法遵守 delegate TR TimeOutDelegate(T param); 形式的方法签名,如有其他需要,可以自行定制也很方便。

[csharp]
namespace TimeOutHelper
{
#region using directives

using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Threading;

#endregion using directives

internal class Program
{
public delegate TR TimeOutDelegate<in T, out TR>(T param);

private static void Main()
{
Dictionary<Guid, string> result;
Console.WriteLine(TimeoutFunction.Execute(Test, "Hello, World!", out result, TimeSpan.FromSeconds(3)));
Console.WriteLine("Hello, World!");
Console.ReadKey();
}

public static Dictionary<Guid, string> Test(string sourceString)
{
var result = sourceString.ToDictionary(
character => Guid.NewGuid(),
character => character.ToString(CultureInfo.InvariantCulture));
Thread.Sleep(4000);
return result;
}

public static class TimeoutFunction
{
/// <summary>
/// Execute a method with timeout check
/// </summary>
/// <typeparam name="T">Target method parameter type</typeparam>
/// <typeparam name="TR">The result type of execution</typeparam>
/// <param name="timeoutMethod">Target method</param>
/// <param name="param">Target method parameter</param>
/// <param name="result">The result of execution</param>
/// <param name="timeout">Set timeout length</param>
/// <returns>Is timeout</returns>
public static Boolean Execute<T, TR>(
TimeOutDelegate<T, TR> timeoutMethod, T param, out TR result, TimeSpan timeout)
{
var asyncResult = timeoutMethod.BeginInvoke(param, null, null);
if (!asyncResult.AsyncWaitHandle.WaitOne(timeout, false))
{
result = default(TR);
return true;
}
result = timeoutMethod.EndInvoke(asyncResult);
return false;
}
}
}
}
[/csharp]

查看原文:http://nap7.com/me/csharpe-timeout-check-method/

C#中,你可以使用`Task` 和 `CancellationTokenSource` 来创建一个超时限制的任务,并在超时执行特定的操作。这里是一个简单的示例: ```csharp using System; using System.Threading.Tasks; class Program { public static async Task Main() { CancellationTokenSource cts = new CancellationTokenSource(); // 设置任务的超时时间,单位是秒 TimeSpan timeout = TimeSpan.FromSeconds(5); // 开始任务并提供取消操作 var task = Task.Run(() => { try { // 这里是你的耗时操作 DoSomethingAsync(cts.Token); } catch (OperationCanceledException) { Console.WriteLine("Task was canceled due to the timeout."); } }, cts.Token); // 等待任务完成,如果超过timeout,则取消任务 if (!await task.WithTimeout(timeout)) { cts.Cancel(); await task; // 确保任务被正确取消 } Console.WriteLine("Task finished or cancelled."); } private static async void DoSomethingAsync(CancellationToken cancellationToken) { // 模拟耗时操作 for (int i = 0; !cancellationToken.IsCancellationRequested && i < 100; i++) { await Task.Delay(100, cancellationToken); Console.WriteLine($"Working... {i}"); } if (!cancellationToken.IsCancellationRequested) Console.WriteLine("Work completed."); } } ``` 在这个例子中,`WithTimeout` 方法用于等待任务,如果在指定时间内任务没有完成,它会返回`false`,这时我们取消`CancellationTokenSource`来停止任务。然后通过`await task`确保任务会被正确地取消。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值