четверг, 6 марта 2014 г.

Немного про обработку исключений

А конкретно про оператор throw и одну особенность его вызова в блоке catch о которой не все знают и даже в MSDN о ней написано чуть более чем ничего. Вот цитата:

The throw statement can be used without an argument, but only if the throw statement is contained within a catch block. In that situation, the throw statement re-throws the error caught by the enclosing catch statement. When an argument is provided, the throw statement throws the value of exception.

На самом деле, основная разница в вызове throw с аргументом и без - в сохранении стека вызова.

Проиллюстрировать эту разницу можно вот такой простой программкой:




        static void Main(string[] args)
        {            

            try {
                OpenFile1("C:\\test.txt");
            }
            catch (Exception e) 
            {
                Console.WriteLine("Exception with throw e;"+Environment.NewLine);
                Console.WriteLine(e.Message);
                Console.WriteLine(e.StackTrace);
            }


            Console.WriteLine();
            Console.WriteLine();

            try
            {
                OpenFile2("C:\\test.txt");
            }
            catch (Exception e)
            {
                Console.WriteLine("Exception with throw;" + Environment.NewLine);
                Console.WriteLine(e.Message);
                Console.WriteLine(e.StackTrace);
            }
            Console.ReadLine();
        }

        //используем throw c аргументом.
        private static void OpenFile1(string filename)
        {
            try
            {
                StreamReader sr = new StreamReader(filename);
            }
            catch (Exception e)
            {
                throw e;
            }

        }

        //используем throw без аргумента
        private static void OpenFile2(string filename)
        {
            try
            {
                StreamReader sr = new StreamReader(filename);
            }
            catch
            {
                throw;
            }

        }

Два метода, пытающиеся отрыть файл, которого у меня нет, абсолютно идентичны за исключением способа вызова throw в случае возникновения ошибки и выбрасывания исключения в процессе открытия файла. Ну и, естественно, содержимого свойства .StackTrace в итоге. Вот результат выполнения этой программы:



Комментариев нет:

Отправить комментарий