简体   繁体   中英

Can't catch exception thrown in derived class

Why base class's try-catch doesn't catches exception thrown in derived class? Did I missed something?

Base class:

public class UmBase
{
    protected Thread ThisThread;

    protected UmBase(int cycleMs, UpdateManager updateManager,
                     string loggerFilename, string loggerFolder = "UpdateManager")
    {
    }

    public void Start()
    {
        ThisThread = new Thread(Work);
        ThisThread.Start();
    }

    public virtual void Iteration()
    {
        throw new Exception("Iteration Method should be overidden!");
    }

    public void Work()
    {
        while (IsProcessing)
        {
            try
            {
                Iteration();
            }
            catch (Exception exception)
            {
                Log.Error(exception.Message); //WANT TO HANDLE IT HERE
            }
            finally
            {
                Sleep(100);
            }
        };
    } 
}

Derived class:

public class ReadParams : UmBase
{
    public ReadParams(UpdateManager updateManager, int cycleMs = 60000)
        : base(cycleMs, updateManager, "sss")
    {
        Iteration();
    } 

    public override void Iteration()
    {
        try
        {
            DbParams.Set(); //EXCEPTION IS THROWN INSIDE
        }
        catch (Exception exception)
        {
            throw new Exception("Oops!", exception);
        }
    }
}

I've read here Can we catch exception from child class method in base class in C#? and can't find my mistake.

Try/Catch will only catch exceptions thrown in the try block. That includes any exceptions thrown by other methods called within the try block. Have you got exceptions configured to break on just unhandled or also on thrown ? See here for how to configure exception breaks

The other possibility is that your exception is being thrown at time of object construction, because your ReadParams constructor calls Iteration() without a try/catch.

ie

public class ReadParams : UmBase
{
    public ReadParams(UpdateManager updateManager, int cycleMs = 60000)
        : base(cycleMs, updateManager, "sss")
    {
        Iteration();
    } 

    public override void Iteration()
    {
        try
        {
            // If throw here (A)
            DbParams.Set(); //EXCEPTION IS THROWN INSIDE
        }
        catch (Exception exception)
        {
            // I'll catch here (A) and then throw a new exception
            throw new Exception("Oops!", exception);
        }
    }
}

public void Work()
{
    while (IsProcessing)
    {
        try
        {
            // Exceptions thrown here including the one you 
            // threw in the method Iteration (B)
            Iteration();
        }
        catch (Exception exception)
        {
            // Will be caught here (B)
            Log.Error(exception.Message); //WANT TO HANDLE IT HERE
        }
        finally
        {
            Sleep(100);
        }
    };
} 

If I read it right, the sequence is:

  1. ReadParams ctor
  2. UmBase ctor
  3. ReadParams Iteration
  4. ReadParams Iteration throw new Exception("Oops!", exception);
  5. Crash... because there is no try-catch in ReadParams ctor

When you override a method you actually replace the entire method wholesale as far as instances of the derived class is concerned.

Unless you call the inherited method explicitly from the overridden one, it is not part of your derived class's logic.

I faced same problem .I noticed one thing but not sure of the reason. When u inherit a base class privately its catch block does not catch the exception of the derived class. inherit the base class publicly and give it a try.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM