I run through millions of records and sometimes I have to debug using Console.WriteLine
to see what is going on.
However, Console.WriteLine
Here is a 7 times faster implementation that bulk-writes to the Console
, with a 10 msec delay. The downside is that you must remember to call Console2.Flush()
at the end of the program, otherwise you may lose some output.
public static class Console2
{
private static readonly StringBuilder _sb = new StringBuilder();
private static volatile CancellationTokenSource _cts;
private static int _count;
public static void Write(string value)
{
lock (_sb) _sb.Append(value);
ScheduleFlush();
}
public static void Write(string format, params object[] args)
{
lock (_sb) _sb.AppendFormat(format, args);
ScheduleFlush();
}
public static void WriteLine(string value)
=> Write(value + Environment.NewLine);
public static void WriteLine(string format, params object[] args)
=> Write(format + Environment.NewLine, args);
public static void WriteLine()
=> WriteLine("");
private static void ScheduleFlush()
{
_cts?.Cancel();
var count = Interlocked.Increment(ref _count);
if (count % 100 == 0) // periodically flush without cancellation
{
var fireAndForget = Task.Run(Flush);
}
else
{
_cts = new CancellationTokenSource();
var token = _cts.Token;
var fireAndForget = Task.Run(async () =>
{
await Task.Delay(10, token);
Flush();
}, token);
}
}
public static void Flush()
{
_cts?.Cancel();
string text;
lock (_sb)
{
if (_sb.Length == 0) return;
text = _sb.ToString();
_sb.Clear();
}
Console.Write(text);
}
}
Usage example:
for (int i = 1; i <= 1000; i++)
{
Console2.WriteLine($"{DateTime.Now:HH:mm:ss.fff} > Line {i}");
}
Console2.Flush();
Output:
06:27:22.882 > Line 1
06:27:22.882 > Line 2
...
06:27:22.893 > Line 999
06:27:22.893 > Line 1000