Mono中的DateTime.ToString返回无效日期(“00/734718/0001 01:41:38”)

问题描述:

我试图让单声道(Debian 2.10.8.1-5)在我的覆盆子pi上与raspbian发行版正常运行(“Debian GNU/Linux wheezy/sid”)。我用apt-get install mono-complete安装了mono。Mono中的DateTime.ToString返回无效日期(“00/734718/0001 01:41:38”)

但是,我遇到了一个我无法弄清楚的有趣问题。 DateTime.ToString()方法返回一个无效的字符串。

下面你可以找到我的示例程序与控制台输出:

using System; 

namespace MonoTest 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      DateTime now = DateTime.Now; 
      Console.WriteLine("Year: " + now.Year); 
      Console.WriteLine("Month: " + now.Month); 
      Console.WriteLine("Day: " + now.Day); 
      Console.WriteLine("DayOfWeek: " + now.DayOfWeek); 
      Console.WriteLine("DateTime.Now: " + DateTime.Now); 
      Console.WriteLine(DateTime.Now.ToString("yyyy-MM-dd")); 
     } 
    } 
} 

输出:

[email protected] ~/bin $ mono MonoTest.exe 
Year: 2012 
Month: 8 
Day: 3 
DayOfWeek: Friday 
DateTime.Now: 00/734718/0001 01:41:38 
0001-00-734718 

有趣的是,734718似乎是经过至今天数自01/01/0001。我在第二块主板上尝试了全新的安装,但都遇到同样的问题。

有没有人有一个想法这里的问题是什么,以及如何说服DateTime.ToString()返回正确的值?

更新(8/4/2012):经过长时间的单声道源代码挖掘后,我能够将问题追溯到System.Math.Floor。显然,它总是返回0。我改变了我的测试程序,以一个简单的:

static void Main(string[] args) 
{ 
    Console.WriteLine("Floor(1.5): " + System.Math.Floor(1.5)); 
} 

在Windows上,结果是“楼(1.5):1”,而在对树莓派我单设置是“地板(1.5 ):0“。我已经看到System.Math.Floor被实现为

[MethodImplAttribute (MethodImplOptions.InternalCall)] 
public extern static double Floor (double d); 

明天,我会进一步探讨这个问题。有谁知道为什么这个问题可能存在?

+0

我也加入了这个问题。你有没有找到解决办法? – Reniuz 2012-08-06 13:18:05

+0

也许相关:'DateTime.Now.ToString(“MM”)'抛出'System.ArgumentOutOfRangeException'在我的覆盆子pi使用单声道2.10.8.1 – weberph 2012-12-30 03:48:12

我无法在Windows上重现您的问题(没有覆盆子,但您的主题为Mono)。

我复制并粘贴您的确切来源Main()到一个新的单控制台应用程序(单声道2.6.1),添加一行(Console.ReadLine();),并运行它:

using System; 

namespace TestDateTimeNow 
{ 

    class MainClass 
    { 
    public static void Main (string[] args) 
    { 
     DateTime now = DateTime.Now; 
     Console.WriteLine("Year: " + now.Year); 
     Console.WriteLine("Month: " + now.Month); 
     Console.WriteLine("Day: " + now.Day); 
     Console.WriteLine("DayOfWeek: " + now.DayOfWeek); 
     Console.WriteLine("DateTime.Now: " + DateTime.Now); 
     Console.WriteLine(DateTime.Now.ToString("yyyy-MM-dd")); 
     Console.ReadLine(); 
    } 
    } 
} 

我得到下面的输出:

Mono App Console App Output

+0

感谢您在Windows上尝试它。我刚刚在Arch Linux 3.1.9-20上尝试了这个树莓派,它的工作原理也是如此。但我仍然不知道为什么它不适用于我的debian安装。 – piglet 2012-08-04 04:33:39

+0

只是一个供参考,在PI运行raspbian(armhf)我不拱门版本,这里是从你的程序的输出中:'单test.exe的 年份:2012 月8日 :20 工作日:周一 日期时间。现在:734735/00/0001 10:18:14 0001-00-734735' – chrispr 2012-08-20 14:23:22

+0

它是一个在hardfp版本的raspbian中一个众所周知的bug,似乎是一个更大的问题,而不仅仅是重新编写几行。 但是,如果您编写自己的“格式字符串”函数,您仍然可以从DateTime类中抽取年份,月份和日期以避开它。只是不要指望toString()格式正确。 – BerggreenDK 2013-02-25 22:31:28

这是最有可能是ARM单二进制层的bug。特别是因为你运行的是Raspberry Pi之前发布的版本。在mono-devel mailing list上你会有更好的运气。这可能已经在git中修复了。

这是单声道的bug #7938,它不仅影响则DateTime.ToString,但是,直接或间接地通过一个浮点数到库调用,用一个Linux发行版的内置ARM上运行时,任何函数硬浮动ABI。有关更多详细信息,请参见C# on Raspberry Pi wiki页面。目前没有很好的解决办法,缺乏运行软浮动发行版。我仍然希望我们很快能够获得固定的单声道运行时。

+0

我同意。 Soft Floating os为我解决了这个问题。 2013-05-29-wheezy-armel.zip – TravisWhidden 2013-09-17 19:43:29

您需要为此使用软浮点操作系统。例如,2013-05-29-wheezy-armel.zip。

硬性浮点不适用于JITers。我有同样的问题,通过在我的RP上安装操作系统的软浮点版本来解决它。我不建议在树莓派平台下使用.net和硬浮点操作系统。希望这可以帮助。