2012-09-19 339 views
13

我需要爲信用卡到期日期生成一個新的Date對象,我只有一個月和一年,我如何根據這兩個生成日期?我需要最簡單的方法。我在這裏閱讀其他一些答案,但他們都似乎太複雜。如何從Java月份和年份生成日期?

+0

你爲什麼不使用1到31之間的任意數字的日子,例如1? – krackmoe

+1

只是新的日期(「2013-04-01」)? – antonpug

+0

不,你必須使用日曆或GregorianCalendar。 但你可以設置日期,月份,年份: set(int year,int month,int date) 和getTime()你得到一個返回的Date對象 – krackmoe

回答

37

你可以使用java.util.Calendar

Calendar calendar = Calendar.getInstance(); 
calendar.clear(); 
calendar.set(Calendar.MONTH, month); 
calendar.set(Calendar.YEAR, year); 
Date date = calendar.getTime(); 
+2

我不能使用新日期(「2013-05-01」)?我在一段時間內沒有用Java編寫程序,但是從大多數語言來看,這似乎是一種常見的方式來做到這一點? – antonpug

+4

作爲一個謹慎的詞,日場將被設置爲今天的日期。如果當前日期超出目標月份的範圍,請檢查預期行爲。例如,設置月份爲二月份時,「日曆」的日期字段爲30.在設置月份和年份之前,將日期設置爲每個月的已知有效值(例如:1)可能是明智的。 –

+0

好點,最好清除所有默認值 – Reimeus

5

可能是一個非答案既然你問了一個java.util.Date,但它似乎是一個好機會指出,隨着Java的日期和時間和日曆最多的工作或許應該與Joda-Time庫來完成,在這種情況下

new LocalDate(year, month, 1) 

想到。

Joda-Time有一些關於本月天的其他好事。例如,如果你想知道當月的第一天,你可以寫

LocalDate firstOfThisMonth = new LocalDate().withDayOfMonth(1); 

在您的評論你問傳遞一個字符串java.util.Date構造函數,例如:

new Date("2012-09-19") 

這版本的構造函數是已棄用,所以不要使用它。您應該創建日期格式化程序並致電parse。這是一個很好的建議,因爲您可能將yearmonth設置爲整數值,並且需要創建一個良好的字符串,正確填充和分隔所有內容,這在所有情況下都難以達到。出於這個原因,使用日期格式化程序,它知道如何完美地處理所有這些東西。

其他更早的答案顯示瞭如何做到這一點。

+0

那麼一個資源,我傳遞這個需要在一個日期,所以,我必須提供。 – antonpug

+0

是的,對不起,我擴大了答案.... –

0

最常見的方法是使用Date(「YYYY-MM-DD」)構造函數,即使它已被棄用。這是即時創建日期的最簡單方法。不管誰決定棄用它。萬歲(「YYYY-MM-DD」)!

+0

該構造函數在不同時區不可靠地工作。總之,它沒有很好地定義你從中得到什麼。你在某個時區的午夜會得到這個日期,這仍然會留下26或27小時變化的空間。構造函數由於某種原因而被棄用。 –

17

java。時間

使用java.time框架構建在Java 8

import java.time.YearMonth; 

int year = 2015; 
int month = 12; 
YearMonth.of(year,month); // 2015-12 

String

YearMonth.parse("2015-12"); // 2015-12 

定製DateTimeFormatter

import java.time.format.DateTimeFormatter; 

DateTimeFormatter formatter = DateTimeFormatter.ofPattern("MM yyyy"); 
YearMonth.parse("12 2015", formatter); // 2015-12 

轉換 要轉換YearMonth更標準的日期表示這是LocalDate

LocalDate startMonth = date.atDay(1); //2015-12-01 
LocalDate endMonth = date.atEndOfMonth(); //2015-12-31 
0

不要使用此答案。通過PrzemekRay Toel使用的答案。正如Przemek所說,傾向於使用YearMonth代表年份和月份。如同所說,如果您必須使用日期,請使用LocalDate,這是一個沒有時間的日期。

如果您絕對需要一個傳統API的老式java.util.Date對象,您無法更改,以下是一種簡單的方法。它可能無法按要求工作,它可能不會給你確切的日期,這取決於你的具體要求。

YearMonth expiration = YearMonth.of(2021, 8); // or .of(2021, Month.AUGUST); 
    Date oldFashionedDateObject = Date.from(expiration 
      .atDay(1) 
      .atStartOfDay(ZoneId.systemDefault()) 
      .toInstant()); 
    System.out.println(oldFashionedDateObject); 

在我的電腦這個打印

Sun Aug 01 00:00:00 CEST 2021 

我們得到的是在我的本地時區首先在午夜月 - 更確切地說,我的JVM的時區設置。這是您的遺留API預期的一個很好的猜測,但它也很危險。 JVM的時區設置可能會在我們的腳下被程序的其他部分或運行在相同JVM中的其他程序改變。換句話說,我們不能確定我們得到了什麼。

如果日期傳輸到計算機上運行不同的時區,比如從客戶端到服務器或反之亦然時區問題變得更糟,或者運行自己的時區數據庫。您的Date將在上個月的時間內發生的風險大約有50%。

如果您知道最後需要的時區,它將有助於指定例如ZoneId.of("America/New_York")而不是上述代碼段中的系統默認值。

如果你的API是寬鬆的,只是需要正確的一個月內的某個時刻,你會好起來給它的UTC月份的第二個或每月的在自己的時區的第三位。這裏是如何做到前者:

Date oldFashionedDateObject = Date.from(expiration 
      .atDay(2) 
      .atStartOfDay(ZoneOffset.UTC) 
      .toInstant()); 
相關問題