出现这种情况是因为当 MSTest 将控制台输出重定向到测试窗口时,它通过CultureInfo.InvariantCulture
to the TextWriter
与控制台关联。
您可以通过以下方式验证这一点:
var threadCulture = Thread.CurrentThread.CurrentCulture;
var consoleCulture = Console.Out.FormatProvider;
Console.WriteLine(threadCulture.Equals(CultureInfo.InvariantCulture));
Console.WriteLine(consoleCulture.Equals(CultureInfo.InvariantCulture));
除非你改变它,否则线程的当前文化通常是这样的en-US
,或者您的计算机设置的任何内容。所以第一项通常是假的。
但第二个项目根据其运行位置而有所不同。作为控制台应用程序,控制台输出区域性应默认为当前线程区域性 - 因此它将为 false。在 XUnit 或 NUnit 测试中,结果也是错误的。但在MSTest中,结果是正确的。
如果你挖掘.NET框架参考源 http://referencesource.microsoft.com/,你会看到
Console.WriteLine calls Out.WriteLine http://referencesource.microsoft.com/#mscorlib/system/console.cs#2113
Out
is a TextWriter
, and TextWriter.WriteLine使用其指定的FormatProvider http://referencesource.microsoft.com/#mscorlib/system/io/textwriter.cs#523
The FormatProvider
或者是null使用当前线程 http://referencesource.microsoft.com/#mscorlib/system/io/textwriter.cs#113, or is 由构造函数参数分配 http://referencesource.microsoft.com/#mscorlib/system/io/textwriter.cs#113.
我认为 MSTest 测试运行程序的源代码不是公开的,但可以得出结论,它们必须在某处执行以下操作:
Console.Out = new SomeWriter(CultureInfo.InvariantCulture);
Where SomeWriter
创建测试输出并继承自TextWriter
.
另一方面,String.Format
将始终使用线程的当前区域性,除非您专门提供不同的区域性。
解决此问题的一种方法是将线程的当前区域性显式设置为不变区域性。
Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture;