如何包含行号和文件名 Console.WriteLine 输出? [复制]

Posted

技术标签:

【中文标题】如何包含行号和文件名 Console.WriteLine 输出? [复制]【英文标题】:How to include line number and file name Console.WriteLine output? [duplicate] 【发布时间】:2014-01-22 18:15:06 【问题描述】:

有没有办法在 C# 的 Console.WriteLine 函数中包含行号和文件名?

例如,在文件“myClass.cs”的第 115 行,我有这样的声明

Console.WriteLine("Hello world");

我希望输出是:

[myClass.cs][115]:  Hello world 

【问题讨论】:

你真的想要这样的输出吗? 看这里:***.com/questions/6369184/… 您想修改 Console.WriteLine 行为来做到这一点,还是只想获取行号?对于行号,检查:***.com/questions/4900744/… 【参考方案1】:

如果您使用的是 C# 5,则可以使用 caller information attributes 来执行此操作。例如:

using System;
using System.IO;
using System.Runtime.CompilerServices;

public class Test

    static void Log(string message,
                    [CallerFilePath] string file = null,
                    [CallerLineNumber] int line = 0)
    
        Console.WriteLine("0 (1): 2", Path.GetFileName(file), line, message);
    

    static void Main()
    
        Log("Hello, world");
        Log("This is the next line");
    

输出:

Test.cs (16): Hello, world
Test.cs (17): This is the next line

在 C# 5 之前,您会遇到执行时堆栈检查,由于内联,这种检查不太可靠,并且依赖于执行时存在的信息。 (例如,它可能不在发布版本中,而上述方法仍然有效。)

【讨论】:

+1 这是一个非常巧妙的技巧 请注意,编译器 正在使用这些属性完成繁重的工作。如果您使用的是 C# 5 编译器,那么即使针对以前的框架版本(或没有这些属性的版本),您也可以拥有这些属性的优点。例如,您可能正在为 Portable Framework 创建一个 MVVM 项目并希望使用CallerMemberNameAttribute,但它在该版本的System.Runtime.CompilerServices 中不存在。如果你手动创建属性并使用它,编译器仍然会尊重并实现它。【参考方案2】:

您可以使用this constructor 检查StackTrace,从中获取StackFrame,然后在StackFrame 上调用GetFileName()GetFileLineNumber()。请注意,这需要应用程序提供 .pdb 文件。

http://social.msdn.microsoft.com/Forums/en-US/a58dc2a0-0612-407b-8cbe-10f1784ba85a/how-to-retreive-the-line-number-and-file-name-of-c-source-code?forum=csharplanguage

来自链接的修改代码:

using System.Diagnostics;

var StackTrace = new System.Diagnostics.StackTrace(true);
var StackFrame = StackTrace.GetFrame(0);
string FileName = StackFrame.GetFileName();
string LineNumber = StackFrame.GetFileLineNumber().ToString();

【讨论】:

【参考方案3】:

我会为此创建一个辅助方法,并利用 Marc Gravell 在这篇文章中所写的解决方案: How do I get the current line number?

类似...

public static class WriteLineHelper

    public static void WriteLine(string message,
        [CallerLineNumber] int lineNumber = 0,
        [CallerMemberName] string caller = null)
    
        Console.WriteLine(string.Format("[0][1] : 2, caller, lineNumber, message);
    

然后在 myClass.cs 中,只需将 Console.WriteLine 的调用替换为:

WriteLineHelper.WriteLine("Hello world.");

【讨论】:

...或者基本上是 Jon Skeet 所说的。

以上是关于如何包含行号和文件名 Console.WriteLine 输出? [复制]的主要内容,如果未能解决你的问题,请参考以下文章

BASH - 将新条目打印到包含行号的文件

如何将文件中的不同行号存储到一个集合中?

如何在 Pentaho Data Integration (Kettle) 中向文件添加行号?

我如何使用libphonenumber查找电话号码?

part01.03 委托与 Lambda 表达式:Lambda 表达式

关于C#的多线程方面