Як надрукувати поточний трас Track у .NET без винятку?


350

У мене є звичайний код C #. У мене немає винятків . Я хочу програмно записувати поточний слід стека для налагодження. Приклад:

public void executeMethod() 
{
    logStackTrace();
    method();
}

Відповіді:


401

Погляньте на System.Diagnosticsпростір імен. Багато смаколиків там!

System.Diagnostics.StackTrace t = new System.Diagnostics.StackTrace();

Це дійсно добре, щоб тикатися, щоб дізнатися, що відбувається під кришкою.

Я рекомендую вам ознайомитись із рішеннями для реєстрації даних (наприклад, NLog, log4net або шаблонами та практиками корпорації Майкрософт), які можуть досягти ваших цілей, а потім і деяких. Успіхів товариш!


74
Майте на увазі , що StackTraceце собака повільно - так що використовуйте його з обережністю.
Джонатан Дікінсон

214

Альтернативою System.Diagnostics.StackTraceє використання System.Environment.StackTrace, який повертає рядкове представлення стека.

Іншим корисним варіантом є використання змінних$CALLER та $CALLSTACK налагодження в Visual Studio, оскільки це може бути включено під час роботи без перебудови програми.


6
Environment.StackTraceщойно новий - це екземпляр StackTrace.
Даніель

9
@Daniel: Так, але це System.Environment.StackTraceможе бути більш зручний спосіб доступу до цієї інформації.
larsmoa

6
@AndreiRinea: Власне, я вірю, що ви можете отримати доступ до номерів рядків за допомогою System.Diagnostics.StackTrace- див. Msdn.microsoft.com/en-us/library/…
larsmoa

5
Чи не дратує те, що Environment.StackTraceзавжди починається з at System.Environment.GetStackTrace(Exception e, Boolean needFileInfo) at System.Environment.get_StackTrace()? Це не є частиною поточного сліду стека, як той момент, коли хтось його шукає.
Рорі

7
@Rory, подивіться на конструктор StackTrace (int skipFrames, bool fNeedFileInfo), ви можете пропустити стартовий кадр. іпен метод в ILSpy, і ви можете побачити, що він робить
Вальтер Веховен

39

Є два способи зробити це. Запис System.Diagnostics.StackTrace()дасть вам стежити за поточним потоком. Якщо у вас є посилання на Threadекземпляр, ви можете отримати слід стека для цього за допомогою перевантаженої версії StackTrace().

Ви також можете перевірити питання про переповнення стека. Як отримати стек -трак поточного потоку? .


16

Ви також можете це зробити у відладчику Visual Studio, не змінюючи код.

  1. Створіть точку перерви, де ви хочете побачити слід стека.
  2. Клацніть правою кнопкою миші та виберіть "Дії ..." у VS2015. У VS2010 виберіть "Коли потрапляє ...", а потім увімкніть "Друк повідомлення".
  3. Переконайтесь, що вибрано "Продовжити виконання".
  4. Введіть текст, який ви хочете роздрукувати.
  5. Додайте $ CALLSTACK там, де ви хочете побачити слід стека.
  6. Запустіть програму у відладчику.

Звичайно, це не допомагає, якщо ви працюєте з кодом на іншій машині, але це може бути досить зручно, якщо ви зможете автоматично виплескати стек стека, не впливаючи на код випуску або навіть не потребуючи перезавантаження програми.


7
Якщо ви хочете побачити слід стека, і ви вже знаходитесь у відладчику VS на точці розриву, просто перейдіть до налагодження-> Windows-> стек викликів.
харгуш

5
Так, але якщо ви зробите це так, програмі не доведеться зупинятися, щоб побачити слід стека.
Ганк Шульц

7
Console.WriteLine(
    new System.Diagnostics.StackTrace().ToString()
    );

Вихід буде подібний до:

на YourNamespace.Program.executeMethod (String msg)

на YourNamespace.Program.Main (String [] args)

Замініть Console.WriteLineсвоїм Logметодом. Насправді, .ToString()у випадку Console.WriteLine, як він приймає, немає потреби object. Але це може знадобитися для вашого методу Log (string msg).


-2
   private void ExceptionTest()
    {
        try
        {
            int j = 0;
            int i = 5;
            i = 1 / j;
        }
        catch (Exception ex)
        {
            Console.WriteLine("Error: " + ex.Message);
            var stList = ex.StackTrace.ToString().Split('\\');
            Console.WriteLine("Exception occurred at " + stList[stList.Count() - 1]);
        }
    }

Здається, працює для мене


3
Це просто породжує очевидний виняток. Чому? Чому б не просто явно створити виняток, а не ваду, що призведе до винятку саме по собі? Яка користь від додаткової логіки лову, необхідної для досягнення фактичного винятку? І навіть тоді ви все ще ігноруєте фактично розміщене запитання про те, як отримати слід без стека без будь-якого винятку (прочитайте заголовок).
Flater

це правдива відповідь, але богові жахливе рішення. НІКОЛИ НЕ БУДЕ ВИКОРИСТОВУВАТИ ... @ Джефф, де б ви це не зробили, замініть його кодом спуску, як інші запропоновані відповіді.
Томер Ш
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.