Threeten, LocalDate kullanarak ayın ilk ve son gününü alın


127

Ayın ilk ve son gününü almam gereken bir Yerel Tarihim var. Bunu nasıl yaparım?

Örneğin. 13/2/2014 Ben almak gerekir 1/2/2014ve 28/2/2014de LOCALDATE formatları.

Threeten LocalDate sınıfını kullanma.

Yanıtlar:


181

Sadece kullanın withDayOfMonthve lengthOfMonth():

LocalDate initial = LocalDate.of(2014, 2, 13);
LocalDate start = initial.withDayOfMonth(1);
LocalDate end = initial.withDayOfMonth(initial.lengthOfMonth());

3
Bilginize Diğer cevapları görüyorum
assylias

147

API, iş gereksinimleriyle yakından eşleşen bir çözümü desteklemek için tasarlanmıştır

import static java.time.temporal.TemporalAdjusters.*;

LocalDate initial = LocalDate.of(2014, 2, 13);
LocalDate start = initial.with(firstDayOfMonth());
LocalDate end = initial.with(lastDayOfMonth());

Ancak Jon'un çözümleri de gayet iyi.


5
Bununla birlikte, bu belirli sorunu çözmek için özel olarak yapılmış API kaynaklarını kullanır.
jpangamarca

90

YearMonth

Bence bütünlük ve daha zarif için, bu YearMonthsınıf kullanımına bakın .

YearMonth month = YearMonth.from(date);
LocalDate start = month.atDay(1);
LocalDate end   = month.atEndOfMonth();

İçinde bulunduğumuz ayın ilk ve son günü için bu şu olur:

LocalDate start = YearMonth.now().atDay(1);
LocalDate end   = YearMonth.now().atEndOfMonth();

8
Hepsinden daha iyi çözüm.
Agustí Sánchez

Ekstra bilgi: YearMonth yearMonth = YearMonth.parse ("202004", DateTimeFormatter.ofPattern ("yyyyMM"));
egemen

LocalDate withyönteme göre avantajları nelerdir?
AndrewBloom

@AndrewBloom, ayın son gününü elde etmek için statik bir işlev kullanmanıza gerek yoktur ve en azından ikinci örnekte, LocalDatebaşlamak için bir örneğiniz olmasına gerek yoktur .
herman

18

Jon Skeets'in cevabı doğru ve benim olumlu oyumu hak etti, tamlık için bu biraz farklı çözümü ekledim:

import static java.time.temporal.TemporalAdjusters.lastDayOfMonth;

LocalDate initial = LocalDate.of(2014, 2, 13);
LocalDate start = initial.withDayOfMonth(1);
LocalDate end = initial.with(lastDayOfMonth());

2
Sevgili olumsuz oy veren, dürüst olmak gerekirse, olumsuz oyu anlamıyorum çünkü cevabım JodaStephen'inkinden bir gün önceydi ve esas olarak ilginç olan yeni kısma, yani ay sonu için zamansal ayarlayıcıya işaret etti. Yani başka kimsenin cevabını "kopyalamadım".
Meno Hochschild

Mükemmel cevap! Bu çözüm daha iyidir çünkü belgelerde önerilmektedir : "... ayın ilk veya son gününü bulmak"
peterchaula

4

Herkes arayan gelirse önceki ayın ilk günü ve önceki ayın son gününde :

public static LocalDate firstDayOfPreviousMonth(LocalDate date) {
        return date.minusMonths(1).withDayOfMonth(1);
    }


public static LocalDate lastDayOfPreviousMonth(LocalDate date) {
        return date.withDayOfMonth(1).minusDays(1);
    }

İyi kod, ancak Stack Overflow'da bir Cevap Sorunun özelliklerini ele almalıdır.
Basil Bourque

Teşekkür ederim, katılıyorum Ben de bunu aramaya geldiğim için bazen ileti dizisinde ilgili kodu buluyoruz. Ben sadece böyle kullanıcılar için koydum. Umarım sorun olmaz. Teşekkürler.
Anil Bhaskar

3
 LocalDate monthstart = LocalDate.of(year,month,1);
 LocalDate monthend = monthstart.plusDays(monthstart.lengthOfMonth()-1);

Lütfen cevabınızı açıklayın
smilyface

1

Özel tarih belirtmekten kaçınmak ve mevcut ayın başlangıç ​​ve bitiş tarihlerini görüntülemeniz gerekiyorsa bunu deneyebilirsiniz:

    LocalDate start = LocalDate.now().minusDays(LocalDate.now().getDayOfMonth()-1);
    LocalDate end = LocalDate.now().minusDays(LocalDate.now().getDayOfMonth()).plusMonths(1);
    System.out.println("Start of month: " + start);
    System.out.println("End of month: " + end);

Sonuç:

>     Start of month: 2019-12-01
>     End of month: 2019-12-30

1
Bana biraz fazla karmaşık görünüyor. Aynı zamanda doğru sonucu vermez. Bu ayın son günü 2019-12-31, ancak pasajınız 2019-12-30 yazdırdı.
Ole VV

0

Bunu dene:

LocalDate initial = LocalDate.of(2014, 2, 13);
LocalDate start = initial.withDayOfMonth(1);         
LocalDate end = initial.withDayOfMonth(initial.getMonthOfYear().getLastDayOfMonth(false));
System.out.println(start);
System.out.println(end);

arzu çıktısını bulabilirsiniz, ancak getLastDayOfMonth yöntemi için true / false parametresine dikkat etmeniz gerekir

bu parametre artık yılı gösterir


Kullanmaya gerek yok getLastDayOfMonth- daha basit bir yaklaşım için cevabıma bakın.
Jon Skeet

0

bunu yalnızca LocalDate sınıfı ile yapmak istiyorsanız:

LocalDate initial = LocalDate.of(2014, 2, 13);

LocalDate start = LocalDate.of(initial.getYear(), initial.getMonthValue(),1);

// Idea: the last day is the same as the first day of next month minus one day.
LocalDate end = LocalDate.of(initial.getYear(), initial.getMonthValue(), 1).plusMonths(1).minusDays(1);

0

@Herman çözümüne yönelik uygulamamı göstermek için buradayım

ZoneId americaLaPazZone = ZoneId.of("UTC-04:00");

static Date firstDateOfMonth(Date date) {
  LocalDate localDate = convertToLocalDateWithTimezone(date);
  YearMonth baseMonth = YearMonth.from(localDate);
  LocalDateTime initialDate = baseMonth.atDay(firstDayOfMonth).atStartOfDay();
  return Date.from(initialDate.atZone(americaLaPazZone).toInstant());
}

static Date lastDateOfMonth(Date date) {
  LocalDate localDate = convertToLocalDateWithTimezone(date);
  YearMonth baseMonth = YearMonth.from(localDate);
  LocalDateTime lastDate = baseMonth.atEndOfMonth().atTime(23, 59, 59);
  return Date.from(lastDate.atZone(americaLaPazZone).toInstant());
}

static LocalDate convertToLocalDateWithTimezone(Date date) {
  return LocalDateTime.from(date.toInstant().atZone(americaLaPazZone)).toLocalDate();
}

LocalDateTimeburada kullanmak için kesinlikle yanlış sınıftır. Değerli bölge / ofset bilgilerini atıyorsunuz.
Basil Bourque

Soru, burada aradığınız zamanla tarih değerlerini değil, yalnızca tarih değerini sorar. Ve korkunç miras sınıfının DateSoru ile hiçbir ilgisi yoktur ve genellikle bundan kaçınılmalıdır.
Fesleğen Bourque

1
La Paz saat dilimi için lütfen daha doğru olanı kullanın ZoneId.of("America/La_Paz"). Bugünkü tarihler için aynı sonucu verecektir, ancak daha sonraki tarihler veya tarihler için olmayabilir.
Ole VV
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.