在方法中使用`try-catch`是不好的做法吗?

时间:2016-02-19 00:43:46

标签: c# exception-handling try-catch

class Program
    {
        public static void Main(string[] args)
        {
            try 
            {
                checkifStringNull(string check)
                Clean();
            }
            catch(ArgumentNullException msg)
            {
                Console.WriteLine(msg.Message);
            }


        }
        public static int Clean()
        {
            List<string> errorLog = new List<string>();

            foreach (DirectoryInfo dir in directories)
            {
                try
                {
                        dir.Delete(true);
                }

                catch(System.UnauthorizedAccessException msg)
                {
                        code = 5;
                        errorLog.Add(String.Concat(dir.FullName," ", code ," ", msg.Message));
                        Console.WriteLine("Error Removing the directory: {0}", dir.FullName);

                }
                catch(System.IO.IOException msg)
                {
                        code = 5;
                        errorLog.Add(String.Concat(dir.FullName," ", code ," ", msg.Message));
                        Console.WriteLine("Error Removing the directory: {0}", dir.FullName);

                }
            }
        }

        public static void checkifStringNull(string check)
        {
            if(string.IsNullOrWhiteSpace(check))
            {
                throw new ArgumentNullException(String.Format("String can't be null"));
            }

        }

我有一个删除特定路径的子目录的方法。如果我在方法中尝试捕获,这没关系吗?原因是我想直接访问抛出异常的循环内的变量(目录),对我来说它更有条理。如果我要从方法中删除代码并将其放在main中,它将如下所示:

public static void Main(string[] args)
{

    try 
    {
        checkifStringNull(string check)
        List<string> errorLog = new List<string>();

    foreach (DirectoryInfo dir in directories)
    {
        try
        {
                dir.Delete(true);
        }

        catch(System.UnauthorizedAccessException msg)
        {
                code = 5;
                errorLog.Add(String.Concat(dir.FullName," ", code ," ", msg.Message));
                Console.WriteLine("Error Removing the directory: {0}", dir.FullName);

        }
        catch(System.IO.IOException msg)
        {
                code = 5;
                errorLog.Add(String.Concat(dir.FullName," ", code ," ", msg.Message));
                Console.WriteLine("Error Removing the directory: {0}", dir.FullName);

        }
    }

    }
    catch(ArgumentNullException msg)
    {
        Console.WriteLine(msg.Message);
    }


}

我在另一个try-catch中嵌入了try-catch,这被认为是不好的做法还是低效的?

2 个答案:

答案 0 :(得分:4)

在方法中使用try-catch并没有错,将try-catch置于另一个try-catch内并没有错。

唯一重要的是处理异常的工作。

你有一个方法,其唯一的工作是尝试执行任务,而不是处理异常情况。该方法不应该捕获异常。

其他时候你有一个方法,你想要处理(几乎)所有特殊情况,否则不会返回控制。此方法将捕获异常,并且可能有很多代码要执行此操作,可能使用嵌套的try-catch es。

现实生活以同样的方式运作。有时候你想让别人尝试给你喝咖啡,但它没有成功(这个地方已经关闭,线路很长)他们应该回来然后你会处理它。其他时候你想让他们出去喝咖啡,而不是空手而归。两者都是完全合法的;这取决于你想要发生什么。这完全是个案的基础。

许多初学者(以及更多!)犯了错误,认为他们应该抓住所有异常并且永远不会抛出异常。这就像一个保姆,认为处理任何异常情况是他们的工作。对于溢出的苏打水可能是真的。但是当窗帘着火时,你可能更喜欢由其他人处理。

答案 1 :(得分:0)

一般情况下 - 没有问题,您可以随时随地抛出或抓住如果有理由这样做,并且您实际上在catch其他{{}}做某事{1}}我不做或者实际需要catch,通常是为了打断当前的流量

在您的示例中,您有一个删除文件夹的循环。如果某个文件夹没有删除,您可能仍希望继续删除,这样您就可以检查IOException或UnauthorizedAccessException(不需要throw前缀,将System.放在类之上)

然而,对于您的using System;,不能说 - 如果您有条件,您可以检查条件并避免抛出异常。抛出异常不是非常高性能的操作,一般应避免使用低成本替代方案,例如ArgumentNullException

if

您的示例的另一个温和问题是,您正在捕获两个不同的异常但执行完全相同的操作。相反,你可以这样做:

if (!string.IsNullOrEmpty(theString)){
  doSomeWork();
} else {
  didNotDoTheWork();// such as Console.WriteLine("Error: theString is empty");
}

使用C#6.0你(VS 2015)你也可以这样做:

try
{
  dir.Delete(true);
} 
catch(Exception x)
{
  if (x is UnauthorizedAccessException || x is IOException){
    Console.WriteLine("Error Removing the directory: {0}", dir.FullName);
  }
  else throw;
}