簡體   English   中英

DateUtils.formatDateRange()格式化日期范圍時出現問題

[英]DateUtils.formatDateRange() issues when formatting date range

在我的應用程序中,我以yyyy-MM-dd的形式從Web服務接收日期(例如2016-03-05 ),並且需要將其格式設置為[縮寫月份] [日期],例如Mar 5 另外,我有一個開始日期和結束日期,並希望將它們顯示為日期范圍,除非兩個日期都相同。

當前,我正在使用DateUtils.formatDateRange() ,它應該滿足我的要求並提供適當的本地化,但是我遇到了兩個問題:

  1. 當我的結束日期是開始日期的第二天時, formatDateRange()僅顯示格式化的開始日期。 例如,如果開始日期為2016-03-05 ,結束日期為2016-03-06 ,則該方法返回Mar 5 (但應為Mar 5 - Mar 6 )。 為什么會這樣?

  2. 當結束日期在同一月份時,不顯示月份。 例如,如果開始日期為2016-03-05 ,結束日期為2016-03-12 ,則該方法返回Mar 5 - 12 有沒有辦法讓它顯示Mar 5 - Mar 12

這是我的代碼:

SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Date startDate, endDate;
try {
    startDate = sdf.parse(startDateString);
    endDate = sdf.parse(endDateString);
} catch (ParseException ignored) {
    return null;
}

int flags = DateUtils.FORMAT_SHOW_DATE | DateUtils.FORMAT_ABBREV_MONTH;
return DateUtils.formatDateRange(context, startDate.getTime(), endDate.getTime(), flags);

在第一種情況下,日期格式正在結束日期范圍內的獨家 (如范圍內反對包括在內 )。 如果您僅在結束日期上加上一毫秒,您將看到預期的范圍,因為現在日期范圍包括午夜的結束日期。

在第二種情況下,恐怕您不符合當前日期格式的語言環境規則。 您幾乎必須接受Android認為是最好的格式,或者針對要支持的每個語言環境提出自己的規則。

tl; dr

LocalDate.parse( inputStart )
         .format( DateTimeFormatter.ofPattern( "MMM d" ).withLocale( Locale.US ) )
+ " - " + 
LocalDate.parse( inputStop )
         .format( DateTimeFormatter.ofPattern( "MMM d" ).withLocale( Locale.US ) )

3月5日-3月6日

細節

您可以使用java.time類非常簡單地完成此操作,而不用麻煩的舊舊日期時間類( DateSimpleDateFormat )和外部庫DateUtils來完成此操作。

您輸入的日期字符串使用標准的ISO 8601格式。 解析/生成字符串時,java.time類默認使用標准格式。 因此,無需指定格式化模式。

LocalDate類表示沒有日期和時區的僅日期值。

LocalDate start = LocalDate.parse( "2017-01-23" );
LocalDate stop = LocalDate.parse( "2017-02-14" );

要生成僅包含縮寫的月份名稱和月份DateTimeFormatter的字符串,請使用DateTimeFormatter

DateTimeFormatter f = DateTimeFormatter.ofPattern( "MMM d" );

指定Locale以確定(a)用於翻譯日名,月名等的人類語言,以及(b)決定縮寫,大寫,標點,分隔符等問題的文化規范。

f = f.withLocale( Locale.US ) ;  // Or Locale.CANADA_FRENCH, Locale.UK, Locale.ITALY, etc.

要求LocalDate生成一個表示其值的字符串。

String output = start.format( f ) + " - " + stop.format( f ) ;

1月23日-2月14日

MonthDay

聽起來好像您可能對MonthDay類感興趣,如果需要使用一個月和一個月中的某天但沒有任何年份的概念。

MonthDay md = MonthDay.of( 1 , 23 ) ;

或使用Month枚舉指定month參數。

MonthDay start = MonthDay.of( Month.JANUARY , 23 ) ;
MonthDay stop = MonthDay.of( Month.FEBRUARY , 14 ) ;

要生成標准ISO 8601格式的字符串,請調用toString

String output = start.toString() ;

--01-23

或使用與上述相同的DateTimeFormatter

String output = start.format( f );

一月23

ISO 8601定義了使用斜杠字符指示時間跨度的格式。 因此,您相同的月日值范圍將是:

String output = start.toString() + "/" + stop.toString() ;

--01-23 /-02-14


關於java.time

java.time框架內置於Java 8及更高版本中。 這些類取代了麻煩的舊的舊式日期時間類,例如java.util.DateCalendarSimpleDateFormat

現在處於維護模式Joda-Time項目建議遷移到java.time類。

要了解更多信息,請參見Oracle教程 並在Stack Overflow中搜索許多示例和說明。 規格為JSR 310

在哪里獲取java.time類?

ThreeTen-Extra項目使用其他類擴展了java.time。 該項目為將來可能在java.time中添加內容提供了一個試驗場。 您可以在這里找到一些有用的類,比如IntervalYearWeekYearQuarter ,和更多

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM