格式化要显示的日期 dd/MM/yyyy

Format Date to display dd/MM/yyyy

我有一种方法可以格式化从服务器获取的日期,格式为 2018-01-18T13:52:49.107Z。我想将此格式转换为仅显示日、月和年,但它不起作用。我如何翻译来自服务器的此响应以显示日期格式。

下面是我的方法:

private String formatDate(String dateString) {
    try {
        SimpleDateFormat sd = new SimpleDateFormat("yyyy-MMM-dd HH:mm:ss.S" );
        Date d = sd.parse(dateString);
        sd = new SimpleDateFormat("dd/MM/yyyy");
        return sd.format(d);
    } catch (ParseException e) {
    }
    return "";
}

尝试更改日期格式 yyyy-MM-dd'T'HH:mm:ss.SSS

private String formatDate(String dateString) {
    try {
        SimpleDateFormat sd = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS" );
        Date d = sd.parse(dateString);
        sd = new SimpleDateFormat("dd/MM/yyyy");
        return sd.format(d);
    } catch (ParseException e) {
    }
    return "";
}

将输入字符串转换为日期

DateFormat inputFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.S");
    Date date = inputFormat.parse(inputString);

将日期格式化为输出格式

DateFormat outputFormat = new SimpleDateFormat("dd-MM-yyyy");
    String outputString = outputFormat.format(date);

这是实现此目的的代码:

import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;

public class DateForm {
    public static void main(String args[]) {
        String formatted = convertDateToReadable("2018-01-18T13:52:49.107Z");
        System.out.println("formatted = " + formatted);
    }


    public static String convertDateToReadable(String dateStr) {
        DateFormat inputFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS", Locale.ENGLISH);
        DateFormat outputFormat = new SimpleDateFormat("yyyy/MM/dd");
        Date formattedDate = null;
        try {
            formattedDate = inputFormat.parse(dateStr);
        } catch (ParseException e) {
            e.printStackTrace();
        }
        String formattedDateStr = outputFormat.format(formattedDate);
        return formattedDateStr;
    }

}

输出=格式化=2018/01/18

请使用这个

SimpleDateFormat sd = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'" );

这是 ISO-DATE 时间格式。 ISO 日期可以加上小时、分钟和秒 (YYYY-MM-DDTHH:MM:SSZ)

日期和时间用大写字母 T 分隔。

UTC 时间定义为大写字母 Z。

private String formatDate(String dateString) {
    try {
        SimpleDateFormat sd = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ" );
        Date d = sd.parse(dateString);
        sd = new SimpleDateFormat("dd/MM/yyyy");
        return sd.format(d);
    } catch (ParseException e) {
    }
    return "";
}

试试这个

 private String formatDate(String dateString) {

    SimpleDateFormat input = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
    SimpleDateFormat output = new SimpleDateFormat("dd/MM/yyyy");

    Date d = null;
    try {
        d = input.parse(dateString);
    } catch (ParseException e) {
        e.printStackTrace();
    }
    String formatted = output.format(d);
    Log.i("DATE", "" + formatted);


    return formatted;
}

输出

TL:DR

private static final DateTimeFormatter dateFormatter
        = DateTimeFormatter.ofPattern("dd/MM/yyyy");

private static String formatDate(String dateString) {
    return Instant.parse(dateString)
            .atZone(ZoneId.of("Pacific/Tarawa"))
            .format(dateFormatter);
}

您需要指定时区

给定你的字符串 2018-01-18T13:52:49.107Z 上面的方法 returns 19/01/201819??是的,当它是 13:52 UTC 时,塔拉瓦环礁已经是第二天了。由于地球上任何地方的日期都不同,因此您需要指定日期所在的时区。因此,如果不是 Pacific/Tarawa,请替换为您想要的时区。例如 Africa/Maputo 或 Asia/Sakhalin。然后您将获得该区域中的日期,并按照指定的格式进行格式化。它不会总是与字符串中的日期(在本例中为 2018 年 1 月 18 日)一致,因为该字符串以 UTC 格式给出日期和时间。要使用用户的时区,您可以尝试指定 ZoneId.systemDefault()。这将使用 JVM 的时区设置。请注意它是脆弱的,您的程序的其他部分或同一 JVM 中的其他程序 运行 可能会在您的脚下更改设置。如果您 did 打算在字符串中使用 UTC 日期,请使用:

    return Instant.parse(dateString)
            .atOffset(ZoneOffset.UTC)
            .format(dateFormatter);

现在结果保证是18/01/2018

java.time

我正在使用 java.time,现代 Java 日期和时间 API。我建议你也这样做。 Date class 早就过时了,而且 SimpleDateFormat 不仅如此,还出了名的麻烦。现代 API 更好用。

问题:我可以在 Android 上使用 java.time 吗?

是的,您可以在 Android 上使用 java.time。它只需要至少 Java 6.

  • 在 Java 8 及更高版本和较新的 Android 设备上,现代 API 是内置的。
  • 在 Java 6 和 7 中获取 ThreeTen Backport,新 classes 的 backport(ThreeTen 用于 JSR 310;请参阅底部的链接)。
  • 在较旧的 Android 上使用 ThreeTen Backport 的 Android 版本。它叫做 ThreeTenABP。并确保使用子包从 org.threeten.bp 导入日期和时间 classes。

你的代码出了什么问题?

您方法中的主要错误(更糟的是使用过时的 classes)在以下两行之间!

    } catch (ParseException e) {
    }

一个空的 catch 吞噬异常 所以你看不到哪里出了问题。永远不要那样做。尝试例如:

    } catch (ParseException e) {
        System.out.println("Message:      " + e.getMessage());
        System.out.println("Error offset: " + e.getErrorOffset());
        if (e.getErrorOffset() != -1) {
            System.out.println("Error text:   " + dateString.substring(e.getErrorOffset()));
        }
    }

这会打印:

Message:      Unparseable date: "2018-01-18T13:52:49.107Z"
Error offset: 5
Error text:   01-18T13:52:49.107Z

因此您的格式化程序无法解析 01,月份。检查 the documentation,它表示关于月份:“如果模式字母的数量为 3 个或更多,则月份被解释为文本;...”。因此,让我们尝试在格式模式字符串中使用 MM 而不是 MMM。现在我们得到:

Message:      Unparseable date: "2018-01-18T13:52:49.107Z"
Error offset: 10
Error text:   T13:52:49.107Z

T 冒犯了。当然,它不在模式字符串中。要指示文字字母是格式的一部分,请将其括起来:yyyy-MM-dd'T'HH:mm:ss.S。下次你的方法 returns:

18/01/2018

我们结束了吗?我会说不是。你忽略了最后的 Z 。它表示与 UTC 或“祖鲁时区”的偏移量 0。如果忽略它,您会将日期时间字符串解析为 JVM 默认时区中的日期时间,这会给出错误的时间。在较新的 Java 版本中,可以使用格式模式字母大写 X 来解析 Z,其中一个、两个或三个。尝试 yyyy-MM-dd'T'HH:mm:ss.SXXX:

Message:      Unparseable date: "2018-01-18T13:52:49.107Z"
Error offset: 22
Error text:   7Z

似乎一个 S 匹配两位数字,10,但不匹配第三位小数,7。我不知道为什么,但让我们放三个,SSS 表示三位小数:yyyy-MM-dd'T'HH:mm:ss.SSSXXX。现在可以了。

链接