从 C# 打印堆栈跟踪信息
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/51768/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Print stack trace information from C#
提问by Lasse V. Karlsen
As part of some error handling in our product, we'd like to dump some stack trace information. However, we experience that many users will simply take a screenshot of the error message dialog instead of sending us a copy of the full report available from the program, and thus I'd like to make some minimal stack trace information available in this dialog.
作为我们产品中某些错误处理的一部分,我们想转储一些堆栈跟踪信息。但是,我们发现许多用户只会截取错误消息对话框的屏幕截图,而不是向我们发送程序提供的完整报告的副本,因此我想在此对话框中提供一些最小的堆栈跟踪信息。
A .NET stack trace on my machine looks like this:
我机器上的 .NET 堆栈跟踪如下所示:
at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
at System.IO.FileStream.Init(String path, FileMode mode, FileAccess access, Int32 rights, Boolean useRights, FileShare share, Int32 bufferSize, FileOptions options, SECURITY_ATTRIBUTES secAttrs, String msgPath, Boolean bFromProxy)
at System.IO.FileStream..ctor(String path, FileMode mode, FileAccess access, FileShare share, Int32 bufferSize, FileOptions options)
at System.IO.StreamReader..ctor(String path, Encoding encoding, Boolean detectEncodingFromByteOrderMarks, Int32 bufferSize)
at System.IO.StreamReader..ctor(String path)
at LVKWinFormsSandbox.MainForm.button1_Click(Object sender, EventArgs e) in C:\Dev\VS.NET\Gatsoft\LVKWinFormsSandbox\MainForm.cs:line 36
I have this question:
我有这个问题:
The format looks to be this:
格式看起来是这样的:
at <class/method> [in file:line ##]
However, the atand inkeywords, I assume these will be localized if they run, say, a norwegian .NET runtime instead of the english one I have installed.
但是,at和in关键字,如果它们运行,例如,挪威语.NET 运行时而不是我安装的英文运行时,我认为它们将被本地化。
Is there any way for me to pick apart this stack trace in a language-neutral manner, so that I can display only the file and line number for those entries that have this?
有什么方法可以让我以一种语言中立的方式来分离这个堆栈跟踪,以便我可以只显示那些具有这个条目的文件和行号?
In other words, I'd like this information from the above text:
换句话说,我想从上面的文字中得到这些信息:
C:\Dev\VS.NET\Gatsoft\LVKWinFormsSandbox\MainForm.cs:line 36
Any advice you can give will be helpful.
您可以提供的任何建议都会有所帮助。
采纳答案by Curt Hagenlocher
You should be able to get a StackTrace object instead of a string by saying
你应该能够通过说得到一个 StackTrace 对象而不是一个字符串
var trace = new System.Diagnostics.StackTrace(exception);
You can then look at the frames yourself without relying on the framework's formatting.
然后,您可以自己查看框架,而无需依赖框架的格式。
See also: StackTrace reference
另请参阅:StackTrace 参考
回答by Greg Ogle
As alternative, log4net, though potentially dangerous, has given me better results than System.Diagnostics. Basically in log4net, you have a method for the various log levels, each with an Exception parameter. So, when you pass the second exception, it will print the stack trace to whichever appender you have configured.
作为替代方案,log4net 虽然有潜在危险,但比 System.Diagnostics 给了我更好的结果。基本上在 log4net 中,您有一个用于各种日志级别的方法,每个级别都有一个 Exception 参数。因此,当您传递第二个异常时,它会将堆栈跟踪打印到您配置的任何附加程序。
example: Logger.Error("Danger!!!", myException );
例子: Logger.Error("Danger!!!", myException );
The output, depending on configuration, looks something like
根据配置,输出看起来像
System.ApplicationException: Something went wrong.
at Adapter.WriteToFile(OleDbCommand cmd) in C:\Adapter.vb:line 35
at Adapter.GetDistributionDocument(Int32 id) in C:\Adapter.vb:line 181
...
回答by Lindholm
Here is the code I use to do this without an exception
这是我用来执行此操作的代码,无一例外
public static void LogStack()
{
var trace = new System.Diagnostics.StackTrace();
foreach (var frame in trace.GetFrames())
{
var method = frame.GetMethod();
if (method.Name.Equals("LogStack")) continue;
Log.Debug(string.Format("{0}::{1}",
method.ReflectedType != null ? method.ReflectedType.Name : string.Empty,
method.Name));
}
}
回答by Hertzel Guinness
Just to make this a 15 sec copy-paste answer:
只是为了使它成为一个 15 秒的复制粘贴答案:
static public string StackTraceToString()
{
StringBuilder sb = new StringBuilder(256);
var frames = new System.Diagnostics.StackTrace().GetFrames();
for (int i = 1; i < frames.Length; i++) /* Ignore current StackTraceToString method...*/
{
var currFrame = frames[i];
var method = currFrame.GetMethod();
sb.AppendLine(string.Format("{0}:{1}",
method.ReflectedType != null ? method.ReflectedType.Name : string.Empty,
method.Name));
}
return sb.ToString();
}
(based on Lindholm answer)
(基于 Lindholm 的回答)
回答by Aftershock
Or there is even shorter version..
或者有更短的版本..
Console.Write(exception.StackTrace);