这是我的代码:
foreach (var pathCartella in folderList)
{
try
{
// some operation
if (txtMonitor.InvokeRequired)
{
txtMonitor.BeginInvoke(new MethodInvoker(delegate { txtMonitor.AppendText(pathCartella + Environment.NewLine); }));
}
}
catch (Exception err)
{
// some operation
return;
}
}
但我注意到,如果我发现异常,return
可以在所有txtMonitor.InvokeRequired
发送到用户界面之前采取行动,并且我丢失了一些“消息”。
我该如何避免这种情况?
答案 0 :(得分:4)
如果我正确理解您的要求,那么您可以使用try / catch块的第三部分 - finally
finally块对于清理分配的任何资源非常有用 试块。控制总是传递给finally块 无论try块如何退出。这个陈述需要 以下表格:
所以你的代码会变成某种形式:
foreach (var pathCartella in folderList)
{
try
{
// some operation
}
catch (Exception err)
{
// some operation
return;
}
finally
{
if (txtMonitor.InvokeRequired)
{
txtMonitor.BeginInvoke(new MethodInvoker(delegate { txtMonitor.AppendText(pathCartella + Environment.NewLine); }));
}
}
}
一些注意事项 - 如果InvokeRequired
为true
,您确定只想运行吗?例如,如果您从简单的按钮单击运行它,而不是从后台线程运行它,则InvokeRequired
将为false
,代码将永远不会执行。
如果您想知道是否总是会被调用,那么这个特殊问题已被多次询问。例如,请参阅If I return out of a try/finally block in C# does the code in the finally always run?。这有一些有趣的反例。
您可以考虑的另一个选择是简单地throw
您的例外。您可以将pathCartella
作为错误消息的一部分传递,以便了解异常发生的路径以及异常。然后您的呼叫者可以处理此问题。例如:
foreach (var pathCartella in folderList)
{
try
{
// some operation
}
catch (Exception err)
{
// some operation
//The original exception becomes the inner exception (so you can get original
//error and stack trace etc). The new exception message contains the path.
throw new Exception(
String.Format("Failed to perform operation on '{0}'", pathCartella),
err);
}
}