Why are try blocks expensive?

2019-01-10 14:22发布

I've heard the advice that you should avoid try catch blocks if possible since they're expensive.

My question is specifically about the .NET platform: Why are try blocks expensive?

Summary of Responses:

There are clearly two camps on this issue: those that say that try blocks are expensive, and those that say "maybe a tiny little bit".

Those that say try blocks are expensive normally mention the "high cost" of unwinding the call stack. Personally, I'm not convinced by that argument - specially after reading about how exceptions handlers are stored here.

Jon Skeet sits on the "maybe a tiny little bit" camp, and has written two articles on exceptions and performance which you can find here.

There was one article that I found extremely interesting: it talked about "other" performance implications of try blocks (not necessarily memory or cpu consumption). Peter Ritchie mentions that he found that code inside try blocks is not optimized as it'd otherwise be by the compiler. You can read about his findings here.

Finally, there's a blog entry about the issue from the man that implemented exceptions in the CLR. Go take a look at Chris Brumme's article here.

11条回答
We Are One
2楼-- · 2019-01-10 14:46

A try block is not expensive at all. Little or no cost is incurred unless an exception is thrown. And if an exception has been thrown, that's an exceptional circumstance and you don't care about performance any more. Does it matter if your program takes 0.001 seconds or 1.0 seconds to fall over? No, it does not. What matters is how good the information reported back to you is so you can fix it and stop it happening again.

查看更多
男人必须洒脱
3楼-- · 2019-01-10 14:49

It's not try blocks you need to worry about as much as catch blocks. And then, it's not that you want to avoid writing the blocks: it's that you want as much as possible to write code that will never actually use them.

查看更多
Rolldiameter
4楼-- · 2019-01-10 14:50

You shouldn't avoid try/catch blocks as that generally means you aren't properly handling exceptions that might occur. Structured Exception Handling (SEH) is only expensive when an exception actually occurs as the runtime must walk the call stack looking for a catch handler, execute that handler (and there may be more than one), then execute the finally blocks, and then return control back to the code at the right location.

Exceptions are not intended to be used to control program logic, but rather to indicate error conditions.

One of the biggest misconceptions about exceptions is that they are for “exceptional conditions.” The reality is that they are for communicating error conditions. From a framework design perspective, there is no such thing as an “exceptional condition”. Whether a condition is exceptional or not depends on the context of usage, --- but reusable libraries rarely know how they will be used. For example, OutOfMemoryException might be exceptional for a simple data entry application; it’s not so exceptional for applications doing their own memory management (e.g. SQL server). In other words, one man’s exceptional condition is another man’s chronic condition. [http://blogs.msdn.com/kcwalina/archive/2008/07/17/ExceptionalError.aspx]

查看更多
爷的心禁止访问
5楼-- · 2019-01-10 14:53

Slightly O/T, but...

There is fairly good design concept that says you should never require exception handling. This means simply that you should be able to query any object for any conditions that might throw an exception before that exception would be thrown.

Like being able to say "writable()" before "write()", stuff like that.

It's a decent idea, and if used, it makes checked exceptions in Java look kind stupid--I mean, checking for a condition and right after that, being forced to still write a try/catch for the same condition?

It's a pretty good pattern, but checked exceptions can be enforced by the compiler, these checks can't. Also not all libraries are made using this design pattern--it's just something to keep in mind when you are thinking about exceptions.

查看更多
来,给爷笑一个
6楼-- · 2019-01-10 14:54

IMO this whole discussion is like saying "wow lops are expensive because I need to increment a counter... i'm not going to use them any more", or "wow creating an object takes time, i'm not going to create a ton of objects any more."

Bottom line is your adding code, presumably for a reason. If the lines of code didn't then incur some overhead, even if its 1 CPU cycle, then why would it exist? Nothing is free.

The wise thing to do, as with any line of code you add to your application, is to only put it there if you need it to do something. If catching an exception is something you need to do, then do it... just like if you need a string to store something, create a new string. By the same means, if you declare a variable that isn't ever used, you are wasting memory and CPU cycles to create it and it should be removed. same with a try/catch.

In other words, if there's code there to do something, then assume that doing something is going to consume CPU and/or memory in some way.

查看更多
登录 后发表回答