Nodatime 格式化特定区域性的长日期模式,但使用其他区域性的月份名称

本文关键字:区域性 其他 模式 格式化 Nodatime 日期 | 更新日期: 2023-09-27 18:34:51

在野田时间中,我想使用特定区域性格式化长日期模式,但使用来自其他区域性的月份名称和日期名称。

我的初始代码是:

var dtfi = (DateTimeFormatInfo) CultureInfo.CurrentCulture.DateTimeFormat.Clone(); // fr-FR
dtfi.DayNames = CultureInfo.CurrentUICulture.DateTimeFormat.DayNames; // en-US
dtfi.MonthNames = CultureInfo.CurrentUICulture.DateTimeFormat.MonthNames;
dtfi.MonthGenitiveNames = CultureInfo.CurrentUICulture.DateTimeFormat.MonthGenitiveNames;
return localDate.ToString("D", dtfi);

克隆日期时间格式不起作用。日期仍然印有日期名称和月份名称,仍然是法语。但是如果我克隆CurrentCulture,它会起作用:

var ci = (CultureInfo) CultureInfo.CurrentCulture.Clone(); // fr-FR
ci.DateTimeFormat.DayNames = CultureInfo.CurrentUICulture.DateTimeFormat.DayNames; // en-US
ci.DateTimeFormat.MonthNames = CultureInfo.CurrentUICulture.DateTimeFormat.MonthNames;
ci.DateTimeFormat.MonthGenitiveNames = CultureInfo.CurrentUICulture.DateTimeFormat.MonthGenitiveNames;
return localDate.ToString("D", ci);

这两个代码片段中,我都跟踪了代码,可以看到在调用 localDate.ToString 之前分配了日期名称、月份名称和月份属名。

谁能解释为什么第一个片段不起作用?

p.s. Noda Time是一个了不起的图书馆,也是我仍然有头发的原因。

Nodatime 格式化特定区域性的长日期模式,但使用其他区域性的月份名称

是的,这是IFormatProvider架构的问题,基本上 - 我们处理得不如我们可能做的那么好。DateTimeFormatInfoCultureInfo都实现了 IFormatProvider ,但为了在某些情况下执行格式化,我们需要的不仅仅是DateTimeFormatInfo - 我们需要NumberFormatInfo(用于正号和负号(和CompareInfo(用于文本比较(。

因此,当我们得到一个不是CultureInfo IFormatInfo时,我们基本上会做错事——我们最终使用了当前的文化。

我们在 github 中遇到了类似问题,但是虽然很明显,如果您只传入一个NumberFormatInfo,则无法在日期/时间设置下获得,但在传入DateTimeFormatInfo时出现问题就不那么明显了。

我可能会让这样的调用抛出带有有用消息的异常,而不仅仅是做错事......或者我可以使用固定文化来获取CompareInfo,如果您传入DateTimeFormatInfo,则可以NumberFormatInfo.

请注意,这最终可能会非常慢,因为我们必须在每次调用时重建内部NodaTimeFormatInfo,因为您在每种情况下都会传入可变DateTimeFormatInfoCultureInfo。最好从CultureInfo创建LocalDatePattern - 在这种情况下,之后不要进一步更改CultureInfo由您决定。(基本上,CultureInfo可变是一个巨大的痛苦。