如何保存控制台应用程序的输出

我需要建议如何让我的C#控制台应用程序通过标准输出向用户显示文本,同时仍然可以在以后访问它。 我想实现的实际function是在程序执行结束时将整个输出缓冲区转储到文本文件中。

我使用的解决方法,虽然我找不到更清晰的方法是子类TextWriter重写写入方法,所以他们都会写入文件并调用原始的stdout编写器。 像这样的东西:

 public class DirtyWorkaround { private class DirtyWriter : TextWriter { private TextWriter stdoutWriter; private StreamWriter fileWriter; public DirtyWriter(string path, TextWriter stdoutWriter) { this.stdoutWriter = stdoutWriter; this.fileWriter = new StreamWriter(path); } override public void Write(string s) { stdoutWriter.Write(s); fileWriter.Write(s); fileWriter.Flush(); } // Same as above for WriteLine() and WriteLine(string), // plus whatever methods I need to override to inherit // from TextWriter (Encoding.Get I guess). } public static void Main(string[] args) { using (DirtyWriter dw = new DirtyWriter("path", Console.Out)) { Console.SetOut(dw); // Teh codez } } } 

看到它一直写入并刷新文件。 我只想在执行结束时才这样做,但我找不到任何方法来访问输出缓冲区。

另外,请原谅上述代码的不准确之处(不得不临时写,抱歉;)。

对此的完美解决方案是将log4net与控制台appender和文件追加器一起使用。 还有许多其他的appender。 它还允许您在运行时关闭和打开不同的appender。

我认为你的方法没有任何问题。

如果你想要可重用的代码,可以考虑实现一个名为MultiWriter的类,或者那些将输入两个(或N?) TextWriter作为输入并将所有的令牌,刷新等分发给这些流的类。 然后你可以做这个文件/控制台的事情,但同样容易分割任何输出流。 有用!

可能不是你想要的,但以防万一……显然, PowerShell实现了一个古老的tee命令的版本。 这完全是出于这个目的。 所以…如果你有他们的话,抽烟吧。

我想说模仿.NET本身使用的诊断(跟踪和调试)。

创建一个“输出”类,它可以具有符合文本输出接口的不同类。 您向输出类报告,它会自动将给定的输出发送给您添加的类(ConsoleOutput,TextFileOutput,WhateverOutput)..依此类推。这也让您打开添加其他“输出”类型(例如xml / xslt获得格式良好的报告?)。

查看Trace Listeners Collection以了解我的意思。

考虑重构您的应用程序以将用户交互部分与业务逻辑分开。 根据我的经验,这种分离对程序的结构非常有益。

对于您在此处尝试解决的特定问题,用户交互部件可以直接将其行为从Console.WriteLine更改为文件I / O.

我正在努力实现一个类似的function来捕获发送到控制台的输出并将其保存到日志中,同时仍然将输出实时传递到正常的控制台,这样它就不会破坏应用程序(例如,如果它是一个控制台应用程序) !)。

如果你仍然试图通过保存控制台输出在自己的代码中执行此操作(而不是使用日志系统来保存您真正关心的信息),我认为您可以在每次写入后避免刷新,只要因为你也覆盖Flush()并确保它刷新你保存的原始stdoutWriter以及stdoutWriter 。 如果应用程序尝试将部分行刷新到控制台以立即显示(例如输入提示,进度指示器等),则要执行此操作,以覆盖正常的行缓冲。

如果该方法的控制台输出缓冲时间过长,则可能需要确保WriteLine()刷新stdoutWriter (但可能不需要刷新stdoutWriter除非调用Flush()重写)。 但我认为原来的Console.Out (实际上是进入控制台)会在换行时自动刷新缓冲区,所以你不必强迫它。

你可能还想覆盖Close()来(刷新和)关闭你的stdoutWriter (也可能是stdoutWriter ),但是我不确定是否真的需要它,或者基础TextWriter中的Close()是否会发出Flush( )(你已经覆盖了),你可能依赖应用程序退出来关闭你的文件。 你可能应该测试它在退出时是否会被刷新,这是肯定的。 并注意exception退出(崩溃)可能不会刷新缓冲输出。 如果这是一个问题,可能需要在换行符上刷新fileWriter ,但这是另一个棘手的蠕虫可以解决的问题。