当前位置: 首页 > 知识库问答 >
问题:

DateTimeFormatter月份模式字母“L”失败

张星洲
2023-03-14
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;

public class Play {
  public static void tryParse(String d,String f) {
    try { 
      LocalDate.parse(d, DateTimeFormatter.ofPattern(f)); 
      System.out.println("Pass");
    } catch (Exception x) {System.out.println("Fail");}
  }
  public static void main(String[] args) {
    tryParse("26-may-2015","dd-L-yyyy");
    tryParse("26-May-2015","dd-L-yyyy");
    tryParse("26-may-2015","dd-LLL-yyyy");
    tryParse("26-May-2015","dd-LLL-yyyy");
    tryParse("26-may-2015","dd-M-yyyy");
    tryParse("26-May-2015","dd-M-yyyy");
    tryParse("26-may-2015","dd-MMM-yyyy");
    tryParse("26-May-2015","dd-MMM-yyyy");
  }
}

只有对tryparse(“26-may-2015”,“dd-Mmm-yyyy”);的最后一次尝试才会“通过”。根据文档,lll应该能够解析出文本格式。还要注意大写的'm'和小写的'm'之间的细微差别。

这真的很烦人,因为我无法在默认情况下解析出Oracle DB默认格式化的字符串

SELECT TO_DATE(SYSDATE,'DD-MON-YYYY') AS dt FROM DUAL;

同样,对于以下程序:

import java.time.LocalDate;
import java.time.format.DateTimeFormatter;

public class Play {
  public static void output(String f) {
    LocalDate d = LocalDate.now();
    Locale l = Locale.US;
    // Locale l = Locale.forLanguageTag("ru");
    System.out.println(d.format(DateTimeFormatter.ofPattern(f,l)));
  }
  public static void main(String[] args) {
    output("dd-L-yyyy");
    output("dd-LLL-yyyy");
    output("dd-M-yyyy");
    output("dd-MMM-yyyy");
  }
}
28-5-2015
28-5-2015
28-5-2015
28-May-2015
28-5-2015
28-Май-2015
28-5-2015
28-мая-2015

我的问题是:

  • 对我来说,期望每一个都能工作是合理的吗?
  • 我们至少应该将其中一些作为bug提交吗?
  • 我是否误解了l模式说明符的用法。

引用文档中的一个部分,我称之为“它很重要”:

  • 针对LLL(长格式文本)问题的Bugfix请求:JDK-8114833(原始oracle Review ID:JI-9021661)
  • 针对小写月份解析问题的增强请求:检查ID:0(这也是一个bug吗??)

共有1个答案

姬俊远
2023-03-14

我认为“L”是指在月份本身使用不同单词的语言,而不是在日期中使用不同的单词。例如:

Locale russian = Locale.forLanguageTag("ru");

asList("MMMM", "LLLL").forEach(ptrn -> 
    System.out.println(ptrn + ": " + ofPattern(ptrn, russian).format(Month.MARCH))
);

产出:

MMMM: марта
LLLL: Март

解析日期时,不应该有任何理由使用“L”而不是“M”。

Arrays.stream(Locale.getAvailableLocales())
    .collect(partitioningBy(
                loc -> "3".equals(Month.MARCH.getDisplayName(FULL_STANDALONE, loc)),
                mapping(Locale::getDisplayLanguage, toCollection(TreeSet::new))
    )).entrySet().forEach(System.out::println);
 类似资料:
  • 问题内容: 我注意到无法按预期解析。见下文: 只有最后一次尝试才会“通过”。按照文档,应该能够解析出文本格式。还要注意大写字母“ M”与小写字母“ m”的细微差别。 这真的很烦人,因为我默认情况下无法解析Oracle DB默认设置格式的字符串 同样,对于以下程序: 我得到以下输出: 显然,格式说明符不处理任何文本内容,对我而言似乎是数字… 但是,如果将Locale更改为,则会得到以下输出: 真的很

  • 运行下面列出的代码时,我看到以下错误: 线程“main”java中出现异常。时间总体安排DateTimeParseException:无法在java的索引4处分析文本“2017年9月21日星期四23:47:03 EDT”。时间总体安排DateTimeFormatter。java上的parseResolved0(未知源)。时间总体安排DateTimeFormatter。在java上解析(未知源)。时

  • 我有以下行在我的代码,我试图格式化一个日期字符串 在第2行,我得到了这个错误: 如何为将给出例如:

  • 问题内容: 是否可以从Joda-Time DateTimeFormatter获取模式字符串? 问题答案: Joda Time无法提供从DateTimeFormatter获取原始模式的方法。原因之一可能是DateTimeFormatter不一定是从模式创建的。例如根本不使用模式。 但是,如果您始终使用模式,则可以包装该类以在构建时记录模式。这样,您以后可以使用简单的静态方法进行查找。例如: 然后,您

  • 我需要以-的格式输出当前日期,即使用ISO周日期,其中一周总是从周一开始,一年的第一周是1月份至少有四天的第一周(因此是1月份有第一个周四的一周)。 由于2015年12月31日为星期四,星期五至星期日,即2016年1月1日至3日,均属2015年第53周(“漫长的一年”),而2016年第一周于1月4日星期一开始。 从DateTimeFormatter规范中,我希望可以使用模式来实现这一点(是,是)。

  • 问题内容: 当我使用上面的语句时,我没有得到错误(我没有使用结尾),但是当我使用下面的语句时,我得到了这个错误: int类型的文字3244444444超出范围 如果使用,则没有错误。 这是什么原因呢?对于长变量,不强制使用l。 问题答案: 被解释为文字整数,但不适合32位变量。它必须是一个 字面量long值 ,因此它需要一个or或末尾: 更多信息: 原始数据类型,特别是 默认值 和 文字 部分。