Visual C# Developer Center > Visual C# Forums > Visual C# Language > C# 'try catch' syntax question
Ask a questionAsk a question
 

AnswerC# 'try catch' syntax question

  • Monday, July 23, 2007 8:59 PMr3gan Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    Hi, a quick question about try / catch syntaxing...  Is it possible to have one catch statement catch multiple exception types, and if so what is the syntax?  Here's an example of what I'm trying to do: 

    Code Snippet

    try

    {

      //

      // do some stuff here

      //

    }

    catch (DirectoryNotFoundException ex)

    {

      MessageBox.Show("Unable to find files!");

    }

    catch (FileNotFoundException ex2)

    {

      MessageBox.Show("Unable to find files!");

    }

    catch (Exception ex3)

    {

      MessageBox.Show("Unable to find files!");

    }

     

     

    As you can see, the above code handles three exception types with the exact same result... how can I put them all in one catch {} block?? As in: 

    Code Snippet

    try

    {

      //

      // do some stuff here

      //

    }

    catch (DirectoryNotFoundException, FileNotFoundException, Exception ex)

    {

      MessageBox.Show("Unable to find files!");

    }

     

     

Answers

  • Monday, July 23, 2007 9:55 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     Answer

    No, you can't with C#.  You can only catch a base exception before derived exceptions.  For example:

    Code Snippet

     try
     {
     }
     catch(ArgumentNullException ane)
     {

    // do something with this specific ArgumentException-derived exception
     }
     catch(ArgumentException ae) 
     {

    // do something with all the other ArgumentException-derived exceptions
     }

     

    You must catch specific exceptions before the general exceptions (i.e. the derived before the base) otherwise you get a compile error because the derived are technically already handled.


     

     

All Replies

  • Monday, July 23, 2007 9:55 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     Answer

    No, you can't with C#.  You can only catch a base exception before derived exceptions.  For example:

    Code Snippet

     try
     {
     }
     catch(ArgumentNullException ane)
     {

    // do something with this specific ArgumentException-derived exception
     }
     catch(ArgumentException ae) 
     {

    // do something with all the other ArgumentException-derived exceptions
     }

     

    You must catch specific exceptions before the general exceptions (i.e. the derived before the base) otherwise you get a compile error because the derived are technically already handled.


     

     

  • Monday, July 23, 2007 11:08 PMr3gan Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
    Alright, thanks for the answer.
  • Wednesday, November 07, 2007 1:32 PMFelixWatts Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

     

    it would be nice though.
  • Wednesday, November 07, 2007 3:54 PMr3gan Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     FelixWatts wrote:

     

    it would be nice though.


    I agree!
  • Wednesday, November 07, 2007 4:38 PMDavin Mickelson Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    Actually, I believe the question was over-analyzed and the answer is yes. Just define one catch block that catches all errors of the base type Exception. The following code snippet will catch any exception that occurs in the try block.

     

    Code Block

    try

    {

      //

      // do some stuff here

      //

    }

    catch (Exception ex)

    {

      MessageBox.Show("Unable to find files!");

    }

     

     

     

    If you need to find out if it was a particular Exception type and gather its associated information, you could try casting it (using is) as certain Exception types and use it's related properties.

    Code Block

    try

    {

      //

      // do some stuff here

      //

    }

    catch (Exception e)

    {

      if (e is FileNotFoundException)

        Console.WriteLine("FileNotFound error: {0}", ((FileNotFoundException)e).FileName);

      else

        Console.WriteLine("Exception error: {0}", e.Message);

    }

     

    Good luck!

  • Wednesday, November 07, 2007 6:08 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     Davin Mickelson wrote:

    Actually, I believe the question was over-analyzed and the answer is yes. Just define one catch block that catches all errors of the base type Exception.

    That was pointed out in July.

  • Wednesday, November 07, 2007 6:16 PMFelixWatts Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    David,

     

    while your suggestion does work (just as well as catching separate exceptions in separate catch blocks and calling the same method in each block), it doesnt actually make the code neat, which is the point of the suggestion.

  • Wednesday, November 07, 2007 6:49 PMDavin Mickelson Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    Peter - in July, you answered no, not yes. Your answer correctly stated how the order of the catch handers must be based on their inheritance (derived before base) but it didn't address the original question "Is it possible to have one catch statement catch multiple exception types, and if so what is the syntax?"

     

    Felix - the original question was not about making the code "neat" but about creating one catch block that can handle multiple exception types.

     

    BTW - VB doesn't raise an error if your catch blocks are in the wrong order. As of .NET 2.0, we now get a VB compiler warning message.

     

    Sorry, guys - I must be totally missing something on this. Please tell me where I'm wrong.

  • Wednesday, November 07, 2007 7:03 PMFelixWatts Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    maybe I misread the originl post, the goal that brought me to this thread was neatness.

     Since you can have

     

    int a, b, c;

     

    why cant you have

     

    catch(SecurityException, UnauthorizedAccessException ex)

    {...}

     

    thats all Smile

  • Wednesday, November 07, 2007 7:10 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     Davin Mickelson wrote:

    Peter - in July, you answered no, not yes. Your answer correctly stated how the order of the catch handers must be based on their inheritance (derived before base) but it didn't address the original question "Is it possible to have one catch statement catch multiple exception types, and if so what is the syntax?"

    No to not being able to specify multiple exceptions types in one block.  There was obviously an implied yes in being able to catch multiple types in one block should the block specific a base exception type... [edit] to which the OP marked the response as the answer.[/edit]

     

    BTW, it's not recommended to create an exception hierarchy that would facilitate doing what the OP wants.

  • Wednesday, November 07, 2007 7:12 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     FelixWatts wrote:

    maybe I misread the originl post, the goal that brought me to this thread was neatness.

     Since you can have

     

    int a, b, c;

     

    why cant you have

     

    catch(SecurityException, UnauthorizedAccessException ex)

    {...}

     

    thats all

    What do you expect to happen when you do this:

    Code Block

    try

    {

    //...

    }

    catch( SecurityException, UnathorizedAccessException ex)

    {

      if(ex.Action == SecurityAction.Assert)

      {

        // do somethiung

      }

    }

     

     

     

  • Wednesday, November 07, 2007 8:34 PMDavin Mickelson Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    "There was obviously an implied yes in being able to catch multiple types in one block should the block specific a base exception type..."

     

    I assumed the OP did not know they could have one catch block of type Exception to handle all exceptions.

     

    Thanks for the clarification, Peter.

  • Thursday, November 08, 2007 12:36 PMFelixWatts Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

     

    Peter,

     

    Good point.

     

    Having considered it: Compiler error. ex should be of the highest common base class type (in this case System.Exception I believe). By definition, if we dont care which of the listed exception types we catch then we don't need type specific fields/props.

  • Thursday, November 08, 2007 3:40 PMr3gan Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     Peter Ritchie wrote:

    What do you expect to happen when you do this:

    Code Block

    try

    {

    //...

    }

    catch( SecurityException, UnathorizedAccessException ex)

    {

      if(ex.Action == SecurityAction.Assert)

      {

        // do somethiung

      }

    }

     


    Actually, Peter, this example does clear up for me my original question.  I was thinking it would be nice to be able to catch multiple exceptions within one catch statement like that (similar to a switch/case being able to run one case logic block for multiple cases) to save from having to type the same exception handling code for many exceptions.  I understand that the base exception can be used after all derrived... but what I forgot is that the exception variable "ex" is of a certain type, and for particular exceptions would contain information that may not be present for other exception types... and I can see how this would cause a compiler or processing error within the exception block of code if it was catching exceptions for multiple derrived types.

    Thanks everybody for your input.
  • Thursday, November 08, 2007 3:59 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     FelixWatts wrote:

     

    Peter,

     

    Good point.

     

    Having considered it: Compiler error. ex should be of the highest common base class type (in this case System.Exception I believe). By definition, if we dont care which of the listed exception types we catch then we don't need type specific fields/props.

    So, that syntax would be to solely perform logic independent of the exceptions caught?  i.e. the exception variable would be effectively pointless.

     

     

    It's reasonably rare to perform exactly the same processing for more than one exception.  Plus this feature doesn't add any new functionality.  i.e. you could do a similar thing with:

     

    Code Block

    try

    {

    }

    catch(Exception ex)

    {

     if(ex is SecurityExcetion || ex is ArgumentException)

     {

     }

     else

       throw;

    }

     

     

     

    So I doubt there's enough benefit for a feature of this nature to make it into the language.

  • Friday, November 09, 2007 11:24 AMFelixWatts Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

     

    r3gan, I still think your idea ia a good one. In the example above ex would be of type System.Exception since that is the common ancestor of SecurityException and UnauthorizedAccessException. We can still use ex.Message etc.

     

    In a case where you want to catch multiple (non related) exception types in a single block then its unlikely you'll need any type specific stuff (like SecurityException.Action or whatever.)

     

    anyhow, it aint gonna happen so.. ho hum. 

  • Friday, November 09, 2007 2:07 PMFelixWatts Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    Peter,

     

    int x, y, z;

     

    doesn't add any extra functionality either. And although I agree that it is /reasonably/ rare to handle unrealted exception types the same, nevertheless I have found myself doing it quite frequesntly lately.

     

    Anyway, I reckon C# will live on and may even continue to flourish without this feature Smile

     

  • Friday, November 09, 2007 3:20 PMPeter RitchieMVP, ModeratorUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
     FelixWatts wrote:

    Peter,

     

    int x, y, z;

     

    doesn't add any extra functionality either. And although I agree that it is /reasonably/ rare to handle unrealted exception types the same, nevertheless I have found myself doing it quite frequesntly lately.

     

    Anyway, I reckon C# will live on and may even continue to flourish without this feature

     

    What was in the language from the very beginning is much different than adding functionality.  When the language was created taking into account programmer's habits and porting code was of high importance.  Additions to the language don't have that issue, normally, and involve ensuring compilers aren't destabilized for no good reason and that it doesn't break existing code.  I don't know if the later applies as I'm not on the compiler team.