By david on May 24, 2010

In .NET, there is a performance penalty when using the try...catch block, in particular when the execution path hits the catch block during runtime. The general "wisdom" is to check for error condition when we can beforehand and only use try...catch if one or more of the methods called in the block may throw an exception that we want to handle (otherwise, let it bubble up as is).

The code is also more readable if we explicitly check for the error condition prior to entering the block rather then let the try...catch block does the error condition. The problem with try...catch used improperly for trapping error condition is the "reactive thought process" of - "What do I do now in the catch block?" I have seen numerous code (including myself before I learned the wisdom) one liner in the catch block that looks :

catch { // do nothing, just make sure we don't get runtime error }

OR

catch { // log error here }

This is a very sloppy programming style.

So, two things to keep in mind when about to use try...catch block:
1. If you can, don't use try...catch block. Maintain good programming style.
2. If the catch block to be executed significantly frequently, there will be noticable performance degradation.

For example, consider a method that attempt to parse an input string and extract some value from it (Assuming the expected input is in the form "Value:[value to extract]" and if input is not in the valid form, return null).

So, instead of the following code

public string ExtractValue(string input) { try { input = input.Trim(); var prefix = "Value:"; if (input.IndexOf(prefix) != 0) return null; return input.SubString(prefix.Length, input.Length-prefix.Length); } catch (Exception exc) { return null; } }

Note that if the function ExtractValue is called many times and the input values being passed are mostly null, it will raise the exception (that would get swallowed due to the catch - so nobody will notice it) - but you will get huge performance hit.


do this:

public string ExtractValue(string input) { if (String.IsNullOrEmpty(input)) return null; var prefix = "Value:"; input = input.Trim(); if (input.IndexOf(prefix) != 0) return null; return input.SubString(prefix.Length, input.Length-prefix.Length); }