1 int iOverTime = 100000;//int.Parse(iniFile.GetString("CATCH", "OVERTIME", ""));//读取超时时间,默认10秒=100000 2 bValue = XCommon.OverTimeCntrol.CallFuncThread(GetArticlePageContent, TimeSpan.FromMilliseconds(iOverTime), null); 3 4 if (!bValue) 5 { 6 strStatus = "读取网址超时(" + iOverTime / 1000 + "秒),跳过!"; 7 } 8 else 9 { 10 ...... 11 }
public static void GetArticlePageContent()
{
}
我要传值进GetArticlePageContent方法和接收它的返回值。 该怎么写?
1 public class OverTimeCntrol 2 { 3 public delegate void Delegate(); 4 5 /// <summary> 6 /// 执行指定的方法,如果在指定的时间之内没有完成,则中止 7 /// </summary> 8 /// <param name="func">任务过程</param> 9 /// <param name="timeSpan">超时时间</param> 10 /// <param name="timeoutCallback">如果超时,则调用该方法</param> 11 /// <returns>是否正确执行完毕</returns> 12 public static bool CallFuncThread(Delegate func, TimeSpan timeSpan, Delegate timeoutCallback) 13 { 14 if (func == null) 15 throw new ArgumentNullException("func"); 16 17 ManualResetEvent resetEvent = new ManualResetEvent(false); 18 ManualResetEvent waitThreadEvent = new ManualResetEvent(false); 19 20 Exception error = null; 21 Thread thread = null; 22 23 // 将任务加到线程当中 24 ThreadPool.QueueUserWorkItem(delegate 25 { 26 27 thread = Thread.CurrentThread; 28 try { func(); } 29 catch (ThreadAbortException) { } 30 catch (Exception ex) { error = ex; } 31 32 resetEvent.Set(); 33 waitThreadEvent.WaitOne(); // 每次线程执行结束都等待后续的处理逻辑 34 }); 35 36 try 37 { 38 bool result = resetEvent.WaitOne(timeSpan, false); // 等待任务的结束 39 40 if (error != null) // 说明在执行过程中出现异常,直接抛出异常 41 throw error; 42 43 if (!result) 44 { 45 if (thread != null) 46 { 47 thread.Abort(); // 此时可以确保该线程没有开始运行新的任务 48 waitThreadEvent.Set(); 49 } 50 51 if (timeoutCallback != null) 52 timeoutCallback(); 53 } 54 55 return result; 56 } 57 finally 58 { 59 waitThreadEvent.Set(); // 最后确保释放线程池线程 60 } 61 } 62 }
这种用法,能获取返回值吗?我增加了你的代码,你看看是否满足需求:
internal class Program { public static void Main(string[] args) { int iOverTime = 10000;//int.Parse(iniFile.GetString("CATCH", "OVERTIME", ""));//读取超时时间,默认10秒=100000 bool bValue = OverTimeCntrol.CallFuncThread(GetArticlePageContent, TimeSpan.FromMilliseconds(iOverTime), null, new object[] { "0", "bbb" }); Console.ReadKey(true); } public static bool GetArticlePageContent(params object[] args) { Thread.Sleep(1000); return true; } } public class OverTimeCntrol { //记录返回值 public static object ReturnVal { get; private set; } public delegate bool Delegate(object[] args);//修改委托,使之可以传入参数 /// <summary> /// 执行指定的方法,如果在指定的时间之内没有完成,则中止 /// </summary> /// <param name="func">任务过程</param> /// <param name="timeSpan">超时时间</param> /// <param name="timeoutCallback">如果超时,则调用该方法</param> /// <param name="args">任务过程所需参数</param> /// <returns>是否正确执行完毕</returns> public static bool CallFuncThread(Delegate func, TimeSpan timeSpan, Action timeoutCallback, params object[] args) { ReturnVal = null;//清空返回值。 if (func == null) throw new ArgumentNullException("func"); ManualResetEvent resetEvent = new ManualResetEvent(false); ManualResetEvent waitThreadEvent = new ManualResetEvent(false); Exception error = null; Thread thread = null; // 将任务加到线程当中 ThreadPool.QueueUserWorkItem(delegate { thread = Thread.CurrentThread; try { ReturnVal=func(args); } catch (ThreadAbortException) { } catch (Exception ex) { error = ex; } resetEvent.Set(); waitThreadEvent.WaitOne(); // 每次线程执行结束都等待后续的处理逻辑 }); try { bool result = resetEvent.WaitOne(timeSpan, false); // 等待任务的结束 if (error != null) // 说明在执行过程中出现异常,直接抛出异常 throw error; if (!result) { if (thread != null) { thread.Abort(); // 此时可以确保该线程没有开始运行新的任务 waitThreadEvent.Set(); } if (timeoutCallback != null) timeoutCallback(); } return result; } finally { waitThreadEvent.Set(); // 最后确保释放线程池线程 } } }
红色部分,是变化的。
不用把委托传进去,委托本身就是一个类,你在类中定义委托后,把方法赋给委托,然后在CallFuncThread方法中调用委托就行了大致如下
public delegate void Delegate;
Delegate delegate = methodName;
public static bool CallFuncThread(TimeSpan timeSpan)
{
//一些操作完成后,开始调用委托中的方法
delegate;
}
亲爱的能不能详细点啊。。。
我的意思是model传值进:GetArticlePageContent这个方法, 并且接收GetArticlePageContent方法的返回值。
bool bValue=false; bValue= XCommon.OverTimeCntrol.CallFuncThread(GetArticlePageContent(model), TimeSpan.FromMilliseconds(iOverTime), null); //CallFuncThread函数会返回一个bool值, 中间的//GetArticlePageContent方法也要返回值; model是要传进去的。。。。这一步就不知道怎么写了。 用out,ref之类的全都有问题。
@问天何必:
是不是就是想把一个方法传给委托然后把委托传到CallFuncThread()这个方法中?
如果 是也好处理啊,定义一个有返回值,有接收参数的委托
public delegate bool Delegate(Model model);
Delegate delegate = GetArticlePageContent;
再把委托传到 CallFuncThread(delegate ,model)并在方法中调用
delegate(model)
这样就OK了
定义一个具有返回值和参数的委托.Func<>就可以吧