使用 SimpleDateFormat 格式化 Java 中的日期

Formatting date in Java using SimpleDateFormat

我正在尝试将日期解析为适当的格式,但我一直收到错误

Unparseable date

谁能告诉我错误是什么?

try {
    System.out.println(new SimpleDateFormat("d-MMM-Y").parse("05-03-2018").toString());
} catch (ParseException e) {
    e.printStackTrace();
}

我希望日期采用这种格式:

05-Mar-18

既然要改格式,先读取并解析Date类型对象中自己格式的日期(从String开始)。然后通过使用 SimpleDateFormat.

将其格式化为新的(所需的)格式来使用该日期对象

您的代码中的错误与 MMMY 有关。 MMM 是字符串中的月份,而您输入的是数值。另外 SimpleDateFormat 中的 Y 是无效年份。 yy是需要添加的。

这里有一个代码可以解决您的问题。

SimpleDateFormat dateFormat = new SimpleDateFormat("d-MM-yyyy");
Date date = dateFormat.parse("05-03-2018");
dateFormat = new SimpleDateFormat("dd-MMM-yy");
System.out.println(dateFormat.format(date));

希望这就是您要找的。

关于日期的一些概念你应该知道。

日期和表示日期的文本之间存在差异

示例:今天的日期是 2018 年 3 月 9 日。那个日期只是一个概念,一个想法 "a specific point in our calendar system".

不过,同一日期可以以多种格式表示。它可以是 "graphical",在一张纸上以圆圈形式围绕一个数字,并以某种特定顺序包含许多其他数字,也可以是 纯文本 ,如:

  • 2018 年 9 月 3 日(day/month/year)
  • 2018 年 3 月 9 日(monty/day/year)
  • 2018-03-09 (ISO8601 format)
  • 2018 年 3 月 9 日
  • 9 de março de 2018(葡萄牙语)
  • 2018年3月5日(日语)
  • 等等...

请注意,文本表示形式不同,但它们都表示相同的日期(相同的值)。

考虑到这一点,让我们看看 Java 如何使用这些概念。

  • 一段文字由String表示。这个 class 包含一个字符序列,仅此而已。这些字符可以代表任何东西;在这种情况下,它是一个日期
  • 日期最初由 java.util.Date 表示,然后由 java.util.Calendar 表示,但 those classes are full of problems and you should avoid them if possible. Today we have a better API for that.

使用 java.time API(或低于 8 的版本 respective backport),您可以使用更简单、更可靠的工具来处理日期。

在您的例子中,您有一个 String(表示日期的文本)并且您想要将其转换为另一种格式。您必须分两步完成:

  1. String 转换为某些 date-type(将文本转换为数值 day/month/year 值)- 这称为 解析
  2. 将此 date-type 值转换为某种格式(将数值转换为特定格式的文本)- 这称为 格式化

对于第 1 步,您可以使用 LocalDate,一种表示日期的类型(日、月和年,没有小时和时区),因为这就是您的输入:

String input = "05-03-2018";
DateTimeFormatter inputParser = DateTimeFormatter.ofPattern("dd-MM-yyyy");
// parse the input
LocalDate date = LocalDate.parse(input, inputParser);

这比 SimpleDateFormat 更可靠,因为它解决了旧 API 的 lots of strange bugs and problems

现在我们有了 LocalDate 对象,我们可以执行第 2 步:

// convert to another format
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("dd-MMM-yy", Locale.ENGLISH);
String output = date.format(formatter);

请注意,我使用了 java.util.Locale。那是因为你想要的输出有一个英文的月份名称,如果你不指定语言环境,它将使用 JVM 的默认值(谁保证它永远是英文?最好告诉 API 您正在使用哪种语言而不是依赖于默认配置,因为这些配置可以随时更改,甚至可以被同一 JVM 中的其他应用程序 运行 更改。

我怎么知道 DateTimeFormatter 中必须使用哪些字母?好吧,我刚读完 javadoc. Many developers ignore the documentation, but we must create the habit to check it, specially the javadoc, that tells you things like the difference between uppercase Y and lowercase y in SimpleDateFormat.