Do Try/Catch Blocks Hurt Performance When Exceptions Are Not Thrown

Do try/catch blocks hurt performance when exceptions are not thrown?

Check it.

static public void Main(string[] args)
{
Stopwatch w = new Stopwatch();
double d = 0;

w.Start();

for (int i = 0; i < 10000000; i++)
{
try
{
d = Math.Sin(1);
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
}

w.Stop();
Console.WriteLine(w.Elapsed);
w.Reset();
w.Start();

for (int i = 0; i < 10000000; i++)
{
d = Math.Sin(1);
}

w.Stop();
Console.WriteLine(w.Elapsed);
}

Output:

00:00:00.4269033  // with try/catch
00:00:00.4260383 // without.

In milliseconds:

449
416

New code:

for (int j = 0; j < 10; j++)
{
Stopwatch w = new Stopwatch();
double d = 0;
w.Start();

for (int i = 0; i < 10000000; i++)
{
try
{
d = Math.Sin(d);
}

catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}

finally
{
d = Math.Sin(d);
}
}

w.Stop();
Console.Write(" try/catch/finally: ");
Console.WriteLine(w.ElapsedMilliseconds);
w.Reset();
d = 0;
w.Start();

for (int i = 0; i < 10000000; i++)
{
d = Math.Sin(d);
d = Math.Sin(d);
}

w.Stop();
Console.Write("No try/catch/finally: ");
Console.WriteLine(w.ElapsedMilliseconds);
Console.WriteLine();
}

New results:

   try/catch/finally: 382
No try/catch/finally: 332

try/catch/finally: 375
No try/catch/finally: 332

try/catch/finally: 376
No try/catch/finally: 333

try/catch/finally: 375
No try/catch/finally: 330

try/catch/finally: 373
No try/catch/finally: 329

try/catch/finally: 373
No try/catch/finally: 330

try/catch/finally: 373
No try/catch/finally: 352

try/catch/finally: 374
No try/catch/finally: 331

try/catch/finally: 380
No try/catch/finally: 329

try/catch/finally: 374
No try/catch/finally: 334

try catch for performance c#

The link I provided in the above comment shows a description of why you shouldn't ever use a try-catch when an if-statement would prevent the exception from being thrown, but in the interest of showing performance in terms of actual numbers, I wrote this quick little test program.

Stopwatch watch = new Stopwatch();

int[] testArray = new int[] { 1, 2, 3, 4, 5 };
int? test = null;

watch.Start();
for (int i = 0; i < 10000; i++)
{
try
{
testArray[(int)test] = 0;
}
catch { }
}
watch.Stop();

Console.WriteLine("try-catch result:");
Console.WriteLine(watch.Elapsed);
Console.WriteLine();

watch.Restart();
for (int i = 0; i < 10000; i++)
{
if (test != null)
testArray[(int)test] = 0;
}
watch.Stop();

Console.WriteLine("if-statement result:");
Console.WriteLine(watch.Elapsed);

The result of the program is this:

try-catch result:
00:00:32.6764911

if-statement result:
00:00:00.0001047

As you can see, the try-catch approach introduces significant overhead when an exception gets caught, taking over 30 seconds to complete 10,000 cycles on my machine. The if-statement, on the other hand, runs so fast that it is basically instantaneous. Compared to the try-catch, this is a performance improvement in the neighborhood of 3,000,000%.

(This isn't a rigorous benchmark, and there are ways to write it and run it differently to get more precise numbers, but this should give you a good idea of just how much more efficient it is to use an if-statement over a try-catch whenever possible.)

does try catch clause affect performance?

Neither try/catch nor try/catch/finally affects performance to any significant degree. Exceptions being created do affect performance, of course (and that is whether they are caught, or not)

Do try/catch blocks hurt performance when exceptions are not thrown?

Is it expensive to use try-catch blocks even if an exception is never thrown?

try has almost no expense at all. Instead of doing the work of setting up the try at runtime, the code's metadata is structured at compile time such that when an exception is thrown, it now does a relatively expensive operation of walking up the stack and seeing if any try blocks exist that would catch this exception. From a layman's perspective, try may as well be free. It's actually throwing the exception that costs you - but unless you're throwing hundreds or thousands of exceptions, you still won't notice the cost.


try has some minor costs associated with it. Java cannot do some optimizations on code in a try block that it would otherwise do. For example, Java will often re-arrange instructions in a method to make it run faster - but Java also needs to guarantee that if an exception is thrown, the method's execution is observed as though its statements, as written in the source code, executed in order up to some line.

Because in a try block an exception can be thrown (at any line in the try block! Some exceptions are thrown asynchronously, such as by calling stop on a Thread (which is deprecated), and even besides that OutOfMemoryError can happen almost anywhere) and yet it can be caught and code continue to execute afterwards in the same method, it is more difficult to reason about optimizations that can be made, so they are less likely to happen. (Someone would have to program the compiler to do them, reason about and guarantee correctness, etc. It'd be a big pain for something meant to be 'exceptional') But again, in practice you won't notice things like this.

Does try-catch block decrease performance

TL;DR NO, exceptions are usually faster on the non-exceptional path compared to error code handling.


Well, the obvious remark is compared to what ?

Compared to not handling the error, it obviously decrease performance; but is performance worth the lack of correctness ? I would argue it is not, so let us supposed that you meant compared to an error code checked with an if statement.

In this case, it depends. There are multiple mechanisms used to implement exceptions. Actually, they can be implemented with a mechanism so close to an if statement that they end up having the same cost (or slightly higher).

In C++ though, all major compilers (gcc introduced it in 4.x serie, MSVC uses it for 64 bits code) now use the Zero-Cost Exception Model. If you read this technical paper that Need4Sleep linked to, it is listed as the table-driven approach. The idea is that for each point of the program that may throw you register in a side-table some bits and pieces that will allow you to find the right catch clause. Honestly, it is a tad more complicated implementation-wise than the older strategies, however the Zero Cost name is derived by the fact that it is free should no exception be thrown. Contrast this to a branch misprediction on a CPU. On the other hand, when an exception is thrown, then the penalty is huge because the table is stored in a cold zone (so likely requires a round-trip to RAM or worse)... but exceptions are exceptional, right ?

To sum up, with modern C++ compilers exceptions are faster than error codes, at the cost of larger binaries (due to the static tables).


For the sake of exhaustiveness, there is a 3rd alternative: abortion. Instead of propagating an error via either status or exception, it is possible to abort the process instead. This is only suitable in a restricted number of situations, however it optimizes better than either alternative.

What is the real overhead of try/catch in C#?

I'm not an expert in language implementations (so take this with a grain of salt), but I think one of the biggest costs is unwinding the stack and storing it for the stack trace. I suspect this happens only when the exception is thrown (but I don't know), and if so, this would be decently sized hidden cost every time an exception is thrown... so it's not like you are just jumping from one place in the code to another, there is a lot going on.

I don't think it's a problem as long as you are using exceptions for EXCEPTIONAL behavior (so not your typical, expected path through the program).

In Javascript, is it expensive to use try-catch blocks even if an exception is never thrown?

Are you doing typical CRUD UI code? Use try catches, use loops that go to 10000 for no reason sprinkled in your code, hell, use angular/ember - you will not notice any performance issue.

If you are doing low level library, physics simulations, games, server-side etc then the never throwing try-catch block wouldn't normally matter at all but the problem is that V8 didn't support it in their optimizing compiler until version 6 of the engine, so the entire containing function that syntactically contains a try catch will not be optimized. You can easily work around this though, by creating a helper function like tryCatch:

function tryCatch(fun) {
try {
return fun();
}
catch(e) {
tryCatch.errorObj.e = e;
return tryCatch.errorObj;
}
}
tryCatch.errorObj = {e: null};


var result = tryCatch(someFunctionThatCouldThrow);
if(result === tryCatch.errorObj) {
//The function threw
var e = result.e;
}
else {
//result is the returned value
}

After V8 version 6 (shipped with Node 8.3 and latest Chrome), the performance of code inside try-catch is the same as that of normal code.



Related Topics



Leave a reply



Submit