我注意到在System.Threading.TimerBase.Dispose()方法中有一个try{} finally{}块,但try{}是空的。

使用try{} finally{}空尝试是否有任何价值?

http://labs.developerfusion.co.uk/SourceViewer/browse.aspx?assembly=SSCLI&namespace=System.Threading&type=TimerBase

[ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
internal bool Dispose(WaitHandle notifyObject)
{
    bool status = false;
    bool bLockTaken = false;
    RuntimeHelpers.PrepareConstrainedRegions();
    try {
    }
    finally {
        do {
            if (Interlocked.CompareExchange(ref m_lock, 1, 0) == 0) {
                bLockTaken = true;
                try {
                    status = DeleteTimerNative(notifyObject.SafeWaitHandle);
                }
                finally {
                    m_lock = 0;
                }
            }
            Thread.SpinWait(1);
            // yield to processor
        }
        while (!bLockTaken);
        GC.SuppressFinalize(this);
    }

    return status;
}

当前回答

从http://blog.somecreativity.com/2008/04/10/the-empty-try-block-mystery/:

This methodology guards against a Thread.Abort call interrupting the processing. The MSDN page of Thread.Abort says that “Unexecuted finally blocks are executed before the thread is aborted”. So in order to guarantee that your processing finishes even if your thread is aborted in the middle by someone calling Abort on your thread, you can place all your code in the finally block (the alternative is to write code in the “catch” block to determine where you were before “try” was interrupted by Abort and proceed from there if you want to).

其他回答

从http://blog.somecreativity.com/2008/04/10/the-empty-try-block-mystery/:

This methodology guards against a Thread.Abort call interrupting the processing. The MSDN page of Thread.Abort says that “Unexecuted finally blocks are executed before the thread is aborted”. So in order to guarantee that your processing finishes even if your thread is aborted in the middle by someone calling Abort on your thread, you can place all your code in the finally block (the alternative is to write code in the “catch” block to determine where you were before “try” was interrupted by Abort and proceed from there if you want to).

这是为了防止线程。中止中断进程。这个方法的文档说:

未执行的finally块在线程中止之前执行。

这是因为为了成功地从错误中恢复,您的代码将需要在错误发生后自行清理。由于c#没有c++风格的析构函数,finally和使用块是确保此类清理可靠执行的唯一可靠方法。记住,使用block会被编译器转换成这样:

try {
    ...
}
finally {
    if(obj != null)
        ((IDisposable)obj).Dispose();
}

在。net 1中。X,有机会finally block会被中止。这种行为在。net 2.0中有所改变。

而且,空的try块永远不会被编译器优化掉。