Iterate between two date ranges with Joda

In my code, I need to iterate over a date range using Joda, and I already tried this:

for(LocalDate currentdate = startDate; currenDate.isBefore(endDate); currenDate= currenDate.plusDays(1)){ System.out.println(currentdate); } 

The above code works, but the iteration stops when currenDate reaches the day before endDate . I want to make iteration stop when currentDate exactly the same as endDate .

 for(Date currentdate = startDate; currentdate <= endDate; currentdate++){ System.out.println(currentdate ); } 

I know that the code above is not possible, but I am doing this to clearly state what I want.

+5
source share
5 answers

There is actually an easy way for your source code that you posted, see my implementation below, just changed your loop implementation:

  //test data LocalDate startDate = LocalDate.now(); //get current date LocalDate endDate = startDate.plusDays(5); //add 5 days to current date System.out.println("startDate : " + startDate); System.out.println("endDate : " + endDate); for(LocalDate currentdate = startDate; currentdate.isBefore(endDate) || currentdate.isEqual(endDate); currentdate= currentdate.plusDays(1)){ System.out.println(currentdate); } 

Below is the output (relative to my localDate):

startDate: 2015-03-26
endDate: 2015-03-31
2015-03-26
2015-03-27
2015-03-28
2015-03-29
2015-03-30
2015-03-31

Hope this helps! Greetings. :)

+7
source

If you want your loop to stop when the date, when the iteration matches the current date, you can use the equality check for this.

Take a look . equals () on LocalDate

Here is a quick example:

 public class DateIterator { public static void main(String[] args) { LocalDate lastMonth = LocalDate.now().minusMonths(1); LocalDate lastWeek = LocalDate.now().minusWeeks(1); LocalDate yesterday = LocalDate.now().minusDays(1); LocalDate today = LocalDate.now(); LocalDate tomorrow = LocalDate.now().plusDays(1); List<LocalDate> dates = Arrays.asList(lastMonth, lastWeek, yesterday, today, tomorrow); for (LocalDate date : dates) { if (date.isEqual(today)) { System.out.println("Date is equal to todays date! Break out, or do something else here"); } else if (date.isBefore(today)) { System.out.println("The date " + date.toString() + " is in the past"); } else { System.out.println("The date " + date.toString() + " is in the future"); } } } } 

Exit:

 The date 2015-02-25 is in the past The date 2015-03-18 is in the past The date 2015-03-24 is in the past Date is equal to todays date! Break out, or do something else here The date 2015-03-26 is in the future 

Obviously, if this equality check passes, you need to exit the loop, etc.

Here's another one that uses a specific date and increments 1 day at a time, which, in my opinion, looks a bit more like what you want

 public class DateIterator { public static void main(String[] args) { LocalDate specificDate = LocalDate.now().minusWeeks(1); LocalDate today = LocalDate.now(); boolean matchFound = false; while (!matchFound) { if (!specificDate.isEqual(today)) { System.out.println(specificDate.toString() + " is in the past, incrementing day and checking again..."); specificDate = specificDate.plusDays(1); } else { System.out.println("Date matches today!"); matchFound = true; } } } } 

Exit:

 2015-03-18 is in the past, incrementing day and checking again... 2015-03-19 is in the past, incrementing day and checking again... 2015-03-20 is in the past, incrementing day and checking again... 2015-03-21 is in the past, incrementing day and checking again... 2015-03-22 is in the past, incrementing day and checking again... 2015-03-23 is in the past, incrementing day and checking again... 2015-03-24 is in the past, incrementing day and checking again... Date matches today! 
+4
source

If you want the loop to include endDate, you can use !currentDate.isAfter( endDate ) . This is logically equivalent to currentDate.isBefore(endDate) || currentDate.equals(endDate) currentDate.isBefore(endDate) || currentDate.equals(endDate) .

The following example will be printed from 6/1/2017 to 6/10/2017.

 LocalDate startDate = new LocalDate( 2017, 6, 1 ); LocalDate endDate = new LocalDate( 2017, 6, 10 ); for ( LocalDate currentDate = startDate; !currentDate.isAfter( endDate ); currentDate = currentDate.plusDays( 1 ) ) { System.out.println( currentDate ); } 
+2
source

Not sure about the style of the jod, but you can iterate at intervals (second, minute, hour, day, month, year) using the Calendar API, here and here are examples

+1
source

Using java.time

The Joda-Time project is now in maintenance mode , with the team advising switching to the java.time classes. See the tutorial from Oracle .

The LocalDate class represents a date value only without time and without a time zone.

 LocalDate start = LocalDate.of( 2017 , Month.JANUARY , 23 ) ; LocalDate stop = LocalDate.of( 2017 , Month.FEBRUARY , 2 ) ; 

By the way, you can add a health check to make sure that the ending is not up to the start.

Not after

I believe that the logic you are looking to include the end date is "not after." The LocalDate class includes the isAfter method, to which you can add the logical "NOT" ( ! ).

In addition, the while seems more appropriate and self-evident in this situation than the for loop.

 LocalDate ld = start ; List<LocalDate> dates = new ArrayList<>() ; while ( ! ld.isAfter( stop ) ) { dates.add( ld ); // Collect this date. ld = ld.plusDays( 1 ) ; // Setup the next loop. } 

See this code run on IdeOne.com .

dates: [2017-01-23, 2017-01-24, 2017-01-25, 2017-01-26, 2017-01-27, 2017-01-28, 2017-01-29, 2017-01-30 , 2017-01-31, 2017-02-01, 2017-02-02]

Half open

iteration stops when currentDate reaches the day before endDate

This is really desirable. Known as Half-Open, the general approach to handling date and time is to treat the beginning as inclusive, while the ending is exceptional. Thus, the lunch break begins at 12:00 (noon) and comes up, but does not include, 13:00:00 (13:00). January starts on January 1 and ends, but does not include February 1. The week starts on Monday and passes, but does not include the following Monday. Most useful, this approach avoids the problem of determining the last split-second date-time when some systems use milliseconds (x.999), some (x.999999), the same nanoseconds (x.999999999), and others use Variations such as 5 decimal places (x.99999). Instead, we approach, but do not include, the first moment of the next hour or day, etc.

I find that using the Half-Open method consistently throughout my code makes the code easier to read, easier to understand, and much less likely to cause errors in turn. I was caught in countless financial secrecy issues that turned out to be confusion or misunderstanding regarding a report covering a date with inclusive and exclusive dates. Therefore, if possible, educate your users to think consistently about Half-Open. If this is not possible, then adjust your code so that your logic and loops at least use Half-Open.

Here is code similar to the above, but using isBefore , and NOT isAfter , use the Half-Open approach. The ending is February 3, not February 2.

 LocalDate start = LocalDate.of( 2017 , Month.JANUARY , 23 ) ; LocalDate stop = LocalDate.of( 2017 , Month.FEBRUARY , 3 ) ; // Third instead of the Second of February, to be half-open. LocalDate ld = start ; List<LocalDate> dates = new ArrayList<>() ; while ( ld.isBefore( stop ) ) { // Using "isBefore" for Half-Open approach. dates.add( ld ); // Collect this date. ld = ld.plusDays( 1 ) ; // Setup the next loop. } 

See this code run on IdeOne.com .

start: 2017-01-23 | stop: 2017-02-03

dates: [2017-01-23, 2017-01-24, 2017-01-25, 2017-01-26, 2017-01-27, 2017-01-28, 2017-01-29, 2017-01-30 , 2017-01-31, 2017-02-01, 2017-02-02]


About java.time

The java.time framework is built into Java 8 and later. These classes supersede the nasty old legacy time classes such as java.util.Date , Calendar and SimpleDateFormat .

The Joda-Time project, now in maintenance mode , we recommend switching to the java.time classes.

To learn more, see the Oracle Tutorial . And search for qaru for many examples and explanations. JSR 310 specification .

Where to get java.time classes?

The ThreeTen-Extra project extends java.time with additional classes. This project is proof of possible future additions to java.time. Here you can find useful classes such as Interval , YearWeek , YearQuarter and more .

+1
source

Source: https://habr.com/ru/post/1216041/


All Articles