十进制.ToString()打印一个带有问号的数字



当在控制台应用程序中以货币模式打印小数时,我试图识别ToString方法的一种奇怪行为。以下代码(sb是StringBuilder,所有变量都是十进制(:

sb
                .Append("Fastest Release: ")
                .Append(TimeSpan.FromSeconds(fastestReleaseSeconds))
                .Append(Environment.NewLine)
                .Append("Average Release Time: ")
                .Append(TimeSpan.FromSeconds(avgReleaseSeconds))
                .Append(Environment.NewLine)
                .Append("Slowest release: ")
                .Append(TimeSpan.FromSeconds(slowestReleaseSeconds))
                .Append(Environment.NewLine);
            sb
                .Append("Total Euro value of Base Currency at engage: ")
                .Append(totValueOfBaseAtEngage.ToString("C", CultureInfo.CurrentCulture))
                .Append(Environment.NewLine)
                .Append("Total current Euro value of base currency: ")
                .Append(totCurrentEuroValueOfBase.ToString("C", CultureInfo.CurrentCulture))
                .Append(Environment.NewLine);
            sb
                .Append("Total Euro value of Quote Currency at engage: ")
                .Append(totValueOfQuoteAtEngage.ToString("C", CultureInfo.CurrentCulture))
                .Append(Environment.NewLine)
                .Append("Total current Euro value of quote currency: ")
                .Append(totCurrentEuroValueOfQuote.ToString("C", CultureInfo.CurrentCulture))
                .Append(Environment.NewLine);

打印以下文本:

最快发布时间:00:00:33

平均发布时间:08:42:48.9952380

最慢发布时间:3.17:39:03

参与时基础货币的欧元总值:2300,00?

基础货币的当前欧元总值:2.208,48?

参与时报价货币的总欧元价值:-2300,00?

报价货币的当前欧元总值:-2.385,44?

问号来自哪里?我尝试了不同的文化,也忽略了这一点,但问号仍然存在。如果我使用不带说明符("C"(的默认ToString((,问号就会消失。

非常感谢Alex

感谢PMF的精彩提示!我的ToString试图打印一个欧元符号,但没有成功。我只是在StringBuilder实例化后添加了Console.OutputEncoding = Encoding.UTF8;,输出正确如下:

参与时基础货币的欧元总价值:2300,00欧元

基础货币的当前欧元总值:22089629780475026176247572537

参与时报价货币的总欧元价值:-23.00,00€

报价货币的当前欧元总值:-23.86,93€

基本增量:-91,04欧元报价增量:-86,93欧元

第二行是一个测试(我删除了"C"格式,看看引擎盖下发生了什么(。

我还测试了Console.OutputEncoding=Encoding.Unicode;`而且效果也很好。

因此,为了了解问题所在,我尝试打印原始编码,如下所示:

var originalEncoding = Console.OutputEncoding;
Console.OutputEncoding = Encoding.Unicode;

sb.Append($"Original Encoding: {originalEncoding}").Append($" Current Encoding: {Console.OutputEncoding}");

并打印

原始编码:System.Text.OSE编码当前编码:System.Text.UnicodeEncoding

页面https://learn.microsoft.com/en-us/dotnet/api/system.text.encoding?view=net-6.0没有提供任何关于OSEncoding的内容,所以我需要更深入地了解这一切的确切含义。再次感谢!

编辑:我在Joel Spolsky网站上找到https://www.joelonsoftware.com/2003/10/08/the-absolute-minimum-every-software-developer-absolutely-positively-must-know-about-unicode-and-character-sets-no-excuses/这是对与Unicode和UTF-8相关的所有内容的一体化解释。我也应该和潜艇船员一起剥洋葱。

此外,MSDN在https://learn.microsoft.com/en-us/dotnet/api/system.console?view=net-6.0(参见"控制台的Unicode支持"one_answers".NET核心注释"(。特别是,调用以获取控制台使用的当前代码页的正确方法是GetConsoleCP。如果Console不是立即可用的有限子集的一部分,并且没有引用System.Text.Encoding.CodePages.dll程序集,则不会说它加载当前区域设置代码页(在我的情况下是意大利语(。