DateTime.ToString в Mono возвращает недействительную дату ( "00/734718/0001 01:41:38" )
Я пытаюсь заставить mono (Debian 2.10.8.1-5) нормально работать на моем малине pi с дистрибутивом raspbian ( "Debian GNU/Linux wheezy/sid" ). Я установил моно с apt-get install mono-complete.
Однако у меня возникает интересная проблема, которую я не могу понять. Метод 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" В то время как моя моно-настройка на малине pi "Floor (1.5): 0". Я видел, что System.Math.Floor реализован как
[MethodImplAttribute (MethodImplOptions.InternalCall)]
public extern static double Floor (double d);
Завтра я рассмотрю этот вопрос. Кто-нибудь знает, почему эта проблема может существовать?
Ответы
Ответ 1
Это ошибка Mono # 7938, и это влияет не только на DateTime.ToString, но и на любую функцию, которая прямо или косвенно передает плавающий - номер точки для вызова библиотеки, при запуске на ARM с дистрибутивом Linux, созданным для ABI с жестким поплавком. Более подробная информация доступна на странице wiki С# на странице малины Pi. В настоящее время нет хорошего решения для этого, за исключением запуска soft-float distro. Я все еще надеюсь, что скоро получим фиксированное моно-исполнение.
Ответ 2
Я не могу воспроизвести вашу проблему в Windows (у вас нет малины, но ваш вопрос говорит Mono
).
Я скопировал и вставил ваш точный источник для Main()
в новое консольное приложение Mono (Mono 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]()
Ответ 3
Это скорее всего будет ошибкой двоичного слоя ARM Mono. Тем более, что вы используете версию, выпущенную до малины Pi. Вам повезет больше с этим в списке рассылки mono-devel. И возможно, что это уже исправлено в git.
Ответ 4
Для этого вам нужно использовать мягкую ОС с плавающей запятой. Например, 2013-05-29-wheezy-armel.zip.
Твердая плавающая точка не работает с JITers. У меня была та же проблема, разрешив ее, установив версию Soft OS с плавающей запятой на мой RP. Я бы не рекомендовал использовать .net с жесткой ОС с плавающей запятой под платформой малины pi. Надеюсь, это поможет.