001 /*
002 * Copyright 2001-2011 Stephen Colebourne
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016 package org.joda.time;
017
018 import java.io.IOException;
019 import java.io.ObjectInputStream;
020 import java.io.ObjectOutputStream;
021 import java.io.Serializable;
022 import java.util.Calendar;
023 import java.util.Date;
024 import java.util.Locale;
025 import java.util.TimeZone;
026
027 import org.joda.convert.FromString;
028 import org.joda.convert.ToString;
029 import org.joda.time.base.BaseLocal;
030 import org.joda.time.chrono.ISOChronology;
031 import org.joda.time.convert.ConverterManager;
032 import org.joda.time.convert.PartialConverter;
033 import org.joda.time.field.AbstractReadableInstantFieldProperty;
034 import org.joda.time.format.DateTimeFormat;
035 import org.joda.time.format.DateTimeFormatter;
036 import org.joda.time.format.ISODateTimeFormat;
037
038 /**
039 * LocalDateTime is an unmodifiable datetime class representing a
040 * datetime without a time zone.
041 * <p>
042 * LocalDateTime implements the {@link ReadablePartial} interface.
043 * To do this, certain methods focus on key fields Year, MonthOfYear,
044 * DayOfYear and MillisOfDay.
045 * However, <b>all</b> fields may in fact be queried.
046 * <p>
047 * Internally, LocalDateTime uses a single millisecond-based value to
048 * represent the local datetime. This value is only used internally and
049 * is not exposed to applications.
050 * <p>
051 * Calculations on LocalDateTime are performed using a {@link Chronology}.
052 * This chronology will be set internally to be in the UTC time zone
053 * for all calculations.
054 *
055 * <p>Each individual field can be queried in two ways:
056 * <ul>
057 * <li><code>getHourOfDay()</code>
058 * <li><code>hourOfDay().get()</code>
059 * </ul>
060 * The second technique also provides access to other useful methods on the
061 * field:
062 * <ul>
063 * <li>numeric value
064 * <li>text value
065 * <li>short text value
066 * <li>maximum/minimum values
067 * <li>add/subtract
068 * <li>set
069 * <li>rounding
070 * </ul>
071 *
072 * <p>
073 * LocalDateTime is thread-safe and immutable, provided that the Chronology is as well.
074 * All standard Chronology classes supplied are thread-safe and immutable.
075 *
076 * @author Stephen Colebourne
077 * @since 1.3
078 */
079 public final class LocalDateTime
080 extends BaseLocal
081 implements ReadablePartial, Serializable {
082
083 /** Serialization lock */
084 private static final long serialVersionUID = -268716875315837168L;
085
086 /** The index of the year field in the field array */
087 private static final int YEAR = 0;
088 /** The index of the monthOfYear field in the field array */
089 private static final int MONTH_OF_YEAR = 1;
090 /** The index of the dayOfMonth field in the field array */
091 private static final int DAY_OF_MONTH = 2;
092 /** The index of the millis field in the field array */
093 private static final int MILLIS_OF_DAY = 3;
094
095 /** The local millis from 1970-01-01T00:00:00 */
096 private final long iLocalMillis;
097 /** The chronology to use in UTC */
098 private final Chronology iChronology;
099
100 //-----------------------------------------------------------------------
101 /**
102 * Obtains a {@code LocalDateTime} set to the current system millisecond time
103 * using <code>ISOChronology</code> in the default time zone.
104 * The resulting object does not use the zone.
105 *
106 * @return the current date, not null
107 * @since 2.0
108 */
109 public static LocalDateTime now() {
110 return new LocalDateTime();
111 }
112
113 /**
114 * Obtains a {@code LocalDateTime} set to the current system millisecond time
115 * using <code>ISOChronology</code> in the specified time zone.
116 * The resulting object does not use the zone.
117 *
118 * @param zone the time zone, not null
119 * @return the current date, not null
120 * @since 2.0
121 */
122 public static LocalDateTime now(DateTimeZone zone) {
123 if (zone == null) {
124 throw new NullPointerException("Zone must not be null");
125 }
126 return new LocalDateTime(zone);
127 }
128
129 /**
130 * Obtains a {@code LocalDateTime} set to the current system millisecond time
131 * using the specified chronology.
132 * The resulting object does not use the zone.
133 *
134 * @param chronology the chronology, not null
135 * @return the current date, not null
136 * @since 2.0
137 */
138 public static LocalDateTime now(Chronology chronology) {
139 if (chronology == null) {
140 throw new NullPointerException("Chronology must not be null");
141 }
142 return new LocalDateTime(chronology);
143 }
144
145 //-----------------------------------------------------------------------
146 /**
147 * Parses a {@code LocalDateTime} from the specified string.
148 * <p>
149 * This uses {@link ISODateTimeFormat#localDateOptionalTimeParser()}.
150 *
151 * @param str the string to parse, not null
152 * @since 2.0
153 */
154 @FromString
155 public static LocalDateTime parse(String str) {
156 return parse(str, ISODateTimeFormat.localDateOptionalTimeParser());
157 }
158
159 /**
160 * Parses a {@code LocalDateTime} from the specified string using a formatter.
161 *
162 * @param str the string to parse, not null
163 * @param formatter the formatter to use, not null
164 * @since 2.0
165 */
166 public static LocalDateTime parse(String str, DateTimeFormatter formatter) {
167 return formatter.parseLocalDateTime(str);
168 }
169
170 //-----------------------------------------------------------------------
171 /**
172 * Constructs a LocalDateTime from a <code>java.util.Calendar</code>
173 * using exactly the same field values.
174 * <p>
175 * Each field is queried from the Calendar and assigned to the LocalDateTime.
176 * This is useful if you have been using the Calendar as a local date,
177 * ignoring the zone.
178 * <p>
179 * One advantage of this method is that this method is unaffected if the
180 * version of the time zone data differs between the JDK and Joda-Time.
181 * That is because the local field values are transferred, calculated using
182 * the JDK time zone data and without using the Joda-Time time zone data.
183 * <p>
184 * This factory method ignores the type of the calendar and always
185 * creates a LocalDateTime with ISO chronology. It is expected that you
186 * will only pass in instances of <code>GregorianCalendar</code> however
187 * this is not validated.
188 *
189 * @param calendar the Calendar to extract fields from
190 * @return the created LocalDateTime
191 * @throws IllegalArgumentException if the calendar is null
192 * @throws IllegalArgumentException if the date is invalid for the ISO chronology
193 */
194 public static LocalDateTime fromCalendarFields(Calendar calendar) {
195 if (calendar == null) {
196 throw new IllegalArgumentException("The calendar must not be null");
197 }
198 return new LocalDateTime(
199 calendar.get(Calendar.YEAR),
200 calendar.get(Calendar.MONTH) + 1,
201 calendar.get(Calendar.DAY_OF_MONTH),
202 calendar.get(Calendar.HOUR_OF_DAY),
203 calendar.get(Calendar.MINUTE),
204 calendar.get(Calendar.SECOND),
205 calendar.get(Calendar.MILLISECOND)
206 );
207 }
208
209 /**
210 * Constructs a LocalDateTime from a <code>java.util.Date</code>
211 * using exactly the same field values.
212 * <p>
213 * Each field is queried from the Date and assigned to the LocalDateTime.
214 * This is useful if you have been using the Date as a local date,
215 * ignoring the zone.
216 * <p>
217 * One advantage of this method is that this method is unaffected if the
218 * version of the time zone data differs between the JDK and Joda-Time.
219 * That is because the local field values are transferred, calculated using
220 * the JDK time zone data and without using the Joda-Time time zone data.
221 * <p>
222 * This factory method always creates a LocalDateTime with ISO chronology.
223 *
224 * @param date the Date to extract fields from
225 * @return the created LocalDateTime
226 * @throws IllegalArgumentException if the calendar is null
227 * @throws IllegalArgumentException if the date is invalid for the ISO chronology
228 */
229 @SuppressWarnings("deprecation")
230 public static LocalDateTime fromDateFields(Date date) {
231 if (date == null) {
232 throw new IllegalArgumentException("The date must not be null");
233 }
234 return new LocalDateTime(
235 date.getYear() + 1900,
236 date.getMonth() + 1,
237 date.getDate(),
238 date.getHours(),
239 date.getMinutes(),
240 date.getSeconds(),
241 (int) (date.getTime() % 1000)
242 );
243 }
244
245 //-----------------------------------------------------------------------
246 /**
247 * Constructs an instance set to the current local time evaluated using
248 * ISO chronology in the default zone.
249 * <p>
250 * Once the constructor is completed, the zone is no longer used.
251 *
252 * @see #now()
253 */
254 public LocalDateTime() {
255 this(DateTimeUtils.currentTimeMillis(), ISOChronology.getInstance());
256 }
257
258 /**
259 * Constructs an instance set to the current local time evaluated using
260 * ISO chronology in the specified zone.
261 * <p>
262 * If the specified time zone is null, the default zone is used.
263 * Once the constructor is completed, the zone is no longer used.
264 *
265 * @param zone the time zone, null means default zone
266 * @see #now(DateTimeZone)
267 */
268 public LocalDateTime(DateTimeZone zone) {
269 this(DateTimeUtils.currentTimeMillis(), ISOChronology.getInstance(zone));
270 }
271
272 /**
273 * Constructs an instance set to the current local time evaluated using
274 * specified chronology.
275 * <p>
276 * If the chronology is null, ISO chronology in the default time zone is used.
277 * Once the constructor is completed, the zone is no longer used.
278 *
279 * @param chronology the chronology, null means ISOChronology in default zone
280 * @see #now(Chronology)
281 */
282 public LocalDateTime(Chronology chronology) {
283 this(DateTimeUtils.currentTimeMillis(), chronology);
284 }
285
286 //-----------------------------------------------------------------------
287 /**
288 * Constructs an instance set to the local time defined by the specified
289 * instant evaluated using ISO chronology in the default zone.
290 * <p>
291 * Once the constructor is completed, the zone is no longer used.
292 *
293 * @param instant the milliseconds from 1970-01-01T00:00:00Z
294 */
295 public LocalDateTime(long instant) {
296 this(instant, ISOChronology.getInstance());
297 }
298
299 /**
300 * Constructs an instance set to the local time defined by the specified
301 * instant evaluated using ISO chronology in the specified zone.
302 * <p>
303 * If the specified time zone is null, the default zone is used.
304 * Once the constructor is completed, the zone is no longer used.
305 *
306 * @param instant the milliseconds from 1970-01-01T00:00:00Z
307 * @param zone the time zone, null means default zone
308 */
309 public LocalDateTime(long instant, DateTimeZone zone) {
310 this(instant, ISOChronology.getInstance(zone));
311 }
312
313 /**
314 * Constructs an instance set to the local time defined by the specified
315 * instant evaluated using the specified chronology.
316 * <p>
317 * If the chronology is null, ISO chronology in the default zone is used.
318 * Once the constructor is completed, the zone is no longer used.
319 *
320 * @param instant the milliseconds from 1970-01-01T00:00:00Z
321 * @param chronology the chronology, null means ISOChronology in default zone
322 */
323 public LocalDateTime(long instant, Chronology chronology) {
324 chronology = DateTimeUtils.getChronology(chronology);
325
326 long localMillis = chronology.getZone().getMillisKeepLocal(DateTimeZone.UTC, instant);
327 iLocalMillis = localMillis;
328 iChronology = chronology.withUTC();
329 }
330
331 //-----------------------------------------------------------------------
332 /**
333 * Constructs an instance from an Object that represents a datetime.
334 * <p>
335 * If the object contains no chronology, <code>ISOChronology</code> is used.
336 * If the object contains no time zone, the default zone is used.
337 * Once the constructor is completed, the zone is no longer used.
338 * <p>
339 * The recognised object types are defined in
340 * {@link org.joda.time.convert.ConverterManager ConverterManager} and
341 * include ReadablePartial, ReadableInstant, String, Calendar and Date.
342 * The String formats are described by {@link ISODateTimeFormat#localDateOptionalTimeParser()}.
343 * The default String converter ignores the zone and only parses the field values.
344 *
345 * @param instant the datetime object
346 * @throws IllegalArgumentException if the instant is invalid
347 */
348 public LocalDateTime(Object instant) {
349 this(instant, (Chronology) null);
350 }
351
352 /**
353 * Constructs an instance from an Object that represents a datetime,
354 * forcing the time zone to that specified.
355 * <p>
356 * If the object contains no chronology, <code>ISOChronology</code> is used.
357 * If the specified time zone is null, the default zone is used.
358 * Once the constructor is completed, the zone is no longer used.
359 * <p>
360 * The recognised object types are defined in
361 * {@link org.joda.time.convert.ConverterManager ConverterManager} and
362 * include ReadablePartial, ReadableInstant, String, Calendar and Date.
363 * The String formats are described by {@link ISODateTimeFormat#localDateOptionalTimeParser()}.
364 * The default String converter ignores the zone and only parses the field values.
365 *
366 * @param instant the datetime object
367 * @param zone the time zone
368 * @throws IllegalArgumentException if the instant is invalid
369 */
370 public LocalDateTime(Object instant, DateTimeZone zone) {
371 PartialConverter converter = ConverterManager.getInstance().getPartialConverter(instant);
372 Chronology chronology = converter.getChronology(instant, zone);
373 chronology = DateTimeUtils.getChronology(chronology);
374 iChronology = chronology.withUTC();
375 int[] values = converter.getPartialValues(this, instant, chronology, ISODateTimeFormat.localDateOptionalTimeParser());
376 iLocalMillis = iChronology.getDateTimeMillis(values[0], values[1], values[2], values[3]);
377 }
378
379 /**
380 * Constructs an instance from an Object that represents a datetime,
381 * using the specified chronology.
382 * <p>
383 * If the chronology is null, ISO in the default time zone is used.
384 * Once the constructor is completed, the zone is no longer used.
385 * <p>
386 * The recognised object types are defined in
387 * {@link org.joda.time.convert.ConverterManager ConverterManager} and
388 * include ReadablePartial, ReadableInstant, String, Calendar and Date.
389 * The String formats are described by {@link ISODateTimeFormat#localDateOptionalTimeParser()}.
390 * The default String converter ignores the zone and only parses the field values.
391 *
392 * @param instant the datetime object
393 * @param chronology the chronology
394 * @throws IllegalArgumentException if the instant is invalid
395 */
396 public LocalDateTime(Object instant, Chronology chronology) {
397 PartialConverter converter = ConverterManager.getInstance().getPartialConverter(instant);
398 chronology = converter.getChronology(instant, chronology);
399 chronology = DateTimeUtils.getChronology(chronology);
400 iChronology = chronology.withUTC();
401 int[] values = converter.getPartialValues(this, instant, chronology, ISODateTimeFormat.localDateOptionalTimeParser());
402 iLocalMillis = iChronology.getDateTimeMillis(values[0], values[1], values[2], values[3]);
403 }
404
405 //-----------------------------------------------------------------------
406 /**
407 * Constructs an instance set to the specified date and time
408 * using <code>ISOChronology</code>.
409 *
410 * @param year the year
411 * @param monthOfYear the month of the year
412 * @param dayOfMonth the day of the month
413 * @param hourOfDay the hour of the day
414 * @param minuteOfHour the minute of the hour
415 */
416 public LocalDateTime(
417 int year,
418 int monthOfYear,
419 int dayOfMonth,
420 int hourOfDay,
421 int minuteOfHour) {
422 this(year, monthOfYear, dayOfMonth, hourOfDay,
423 minuteOfHour, 0, 0, ISOChronology.getInstanceUTC());
424 }
425
426 /**
427 * Constructs an instance set to the specified date and time
428 * using <code>ISOChronology</code>.
429 *
430 * @param year the year
431 * @param monthOfYear the month of the year
432 * @param dayOfMonth the day of the month
433 * @param hourOfDay the hour of the day
434 * @param minuteOfHour the minute of the hour
435 * @param secondOfMinute the second of the minute
436 */
437 public LocalDateTime(
438 int year,
439 int monthOfYear,
440 int dayOfMonth,
441 int hourOfDay,
442 int minuteOfHour,
443 int secondOfMinute) {
444 this(year, monthOfYear, dayOfMonth, hourOfDay,
445 minuteOfHour, secondOfMinute, 0, ISOChronology.getInstanceUTC());
446 }
447
448 /**
449 * Constructs an instance set to the specified date and time
450 * using <code>ISOChronology</code>.
451 *
452 * @param year the year
453 * @param monthOfYear the month of the year
454 * @param dayOfMonth the day of the month
455 * @param hourOfDay the hour of the day
456 * @param minuteOfHour the minute of the hour
457 * @param secondOfMinute the second of the minute
458 * @param millisOfSecond the millisecond of the second
459 */
460 public LocalDateTime(
461 int year,
462 int monthOfYear,
463 int dayOfMonth,
464 int hourOfDay,
465 int minuteOfHour,
466 int secondOfMinute,
467 int millisOfSecond) {
468 this(year, monthOfYear, dayOfMonth, hourOfDay,
469 minuteOfHour, secondOfMinute, millisOfSecond, ISOChronology.getInstanceUTC());
470 }
471
472 /**
473 * Constructs an instance set to the specified date and time
474 * using the specified chronology, whose zone is ignored.
475 * <p>
476 * If the chronology is null, <code>ISOChronology</code> is used.
477 *
478 * @param year the year
479 * @param monthOfYear the month of the year
480 * @param dayOfMonth the day of the month
481 * @param hourOfDay the hour of the day
482 * @param minuteOfHour the minute of the hour
483 * @param secondOfMinute the second of the minute
484 * @param millisOfSecond the millisecond of the second
485 * @param chronology the chronology, null means ISOChronology in default zone
486 */
487 public LocalDateTime(
488 int year,
489 int monthOfYear,
490 int dayOfMonth,
491 int hourOfDay,
492 int minuteOfHour,
493 int secondOfMinute,
494 int millisOfSecond,
495 Chronology chronology) {
496 super();
497 chronology = DateTimeUtils.getChronology(chronology).withUTC();
498 long instant = chronology.getDateTimeMillis(year, monthOfYear, dayOfMonth,
499 hourOfDay, minuteOfHour, secondOfMinute, millisOfSecond);
500 iChronology = chronology;
501 iLocalMillis = instant;
502 }
503
504 /**
505 * Handle broken serialization from other tools.
506 * @return the resolved object, not null
507 */
508 private Object readResolve() {
509 if (iChronology == null) {
510 return new LocalDateTime(iLocalMillis, ISOChronology.getInstanceUTC());
511 }
512 if (DateTimeZone.UTC.equals(iChronology.getZone()) == false) {
513 return new LocalDateTime(iLocalMillis, iChronology.withUTC());
514 }
515 return this;
516 }
517
518 //-----------------------------------------------------------------------
519 /**
520 * Gets the number of fields in this partial, which is four.
521 * The supported fields are Year, MonthOfDay, DayOfMonth and MillisOfDay.
522 *
523 * @return the field count, four
524 */
525 public int size() {
526 return 4;
527 }
528
529 /**
530 * Gets the field for a specific index in the chronology specified.
531 * <p>
532 * This method must not use any instance variables.
533 *
534 * @param index the index to retrieve
535 * @param chrono the chronology to use
536 * @return the field
537 */
538 protected DateTimeField getField(int index, Chronology chrono) {
539 switch (index) {
540 case YEAR:
541 return chrono.year();
542 case MONTH_OF_YEAR:
543 return chrono.monthOfYear();
544 case DAY_OF_MONTH:
545 return chrono.dayOfMonth();
546 case MILLIS_OF_DAY:
547 return chrono.millisOfDay();
548 default:
549 throw new IndexOutOfBoundsException("Invalid index: " + index);
550 }
551 }
552
553 /**
554 * Gets the value of the field at the specifed index.
555 * <p>
556 * This method is required to support the <code>ReadablePartial</code>
557 * interface. The supported fields are Year, MonthOfDay, DayOfMonth and MillisOfDay.
558 *
559 * @param index the index, zero to two
560 * @return the value
561 * @throws IndexOutOfBoundsException if the index is invalid
562 */
563 public int getValue(int index) {
564 switch (index) {
565 case YEAR:
566 return getChronology().year().get(getLocalMillis());
567 case MONTH_OF_YEAR:
568 return getChronology().monthOfYear().get(getLocalMillis());
569 case DAY_OF_MONTH:
570 return getChronology().dayOfMonth().get(getLocalMillis());
571 case MILLIS_OF_DAY:
572 return getChronology().millisOfDay().get(getLocalMillis());
573 default:
574 throw new IndexOutOfBoundsException("Invalid index: " + index);
575 }
576 }
577
578 //-----------------------------------------------------------------------
579 /**
580 * Get the value of one of the fields of a datetime.
581 * <p>
582 * This method gets the value of the specified field.
583 * For example:
584 * <pre>
585 * DateTime dt = new DateTime();
586 * int year = dt.get(DateTimeFieldType.year());
587 * </pre>
588 *
589 * @param type a field type, usually obtained from DateTimeFieldType, not null
590 * @return the value of that field
591 * @throws IllegalArgumentException if the field type is null
592 */
593 public int get(DateTimeFieldType type) {
594 if (type == null) {
595 throw new IllegalArgumentException("The DateTimeFieldType must not be null");
596 }
597 return type.getField(getChronology()).get(getLocalMillis());
598 }
599
600 /**
601 * Checks if the field type specified is supported by this
602 * local datetime and chronology.
603 * This can be used to avoid exceptions in {@link #get(DateTimeFieldType)}.
604 *
605 * @param type a field type, usually obtained from DateTimeFieldType
606 * @return true if the field type is supported
607 */
608 public boolean isSupported(DateTimeFieldType type) {
609 if (type == null) {
610 return false;
611 }
612 return type.getField(getChronology()).isSupported();
613 }
614
615 /**
616 * Checks if the duration type specified is supported by this
617 * local datetime and chronology.
618 *
619 * @param type a duration type, usually obtained from DurationFieldType
620 * @return true if the field type is supported
621 */
622 public boolean isSupported(DurationFieldType type) {
623 if (type == null) {
624 return false;
625 }
626 return type.getField(getChronology()).isSupported();
627 }
628
629 //-----------------------------------------------------------------------
630 /**
631 * Gets the milliseconds of the datetime instant from the Java epoch
632 * of 1970-01-01T00:00:00 (not fixed to any specific time zone).
633 *
634 * @return the number of milliseconds since 1970-01-01T00:00:00
635 * @since 1.5 (previously private)
636 */
637 protected long getLocalMillis() {
638 return iLocalMillis;
639 }
640
641 /**
642 * Gets the chronology of the datetime.
643 *
644 * @return the Chronology that the datetime is using
645 */
646 public Chronology getChronology() {
647 return iChronology;
648 }
649
650 //-----------------------------------------------------------------------
651 /**
652 * Compares this ReadablePartial with another returning true if the chronology,
653 * field types and values are equal.
654 *
655 * @param partial an object to check against
656 * @return true if fields and values are equal
657 */
658 public boolean equals(Object partial) {
659 // override to perform faster
660 if (this == partial) {
661 return true;
662 }
663 if (partial instanceof LocalDateTime) {
664 LocalDateTime other = (LocalDateTime) partial;
665 if (iChronology.equals(other.iChronology)) {
666 return iLocalMillis == other.iLocalMillis;
667 }
668 }
669 return super.equals(partial);
670 }
671
672 /**
673 * Compares this partial with another returning an integer
674 * indicating the order.
675 * <p>
676 * The fields are compared in order, from largest to smallest.
677 * The first field that is non-equal is used to determine the result.
678 * <p>
679 * The specified object must be a partial instance whose field types
680 * match those of this partial.
681 *
682 * @param partial an object to check against
683 * @return negative if this is less, zero if equal, positive if greater
684 * @throws ClassCastException if the partial is the wrong class
685 * or if it has field types that don't match
686 * @throws NullPointerException if the partial is null
687 */
688 public int compareTo(ReadablePartial partial) {
689 // override to perform faster
690 if (this == partial) {
691 return 0;
692 }
693 if (partial instanceof LocalDateTime) {
694 LocalDateTime other = (LocalDateTime) partial;
695 if (iChronology.equals(other.iChronology)) {
696 return (iLocalMillis < other.iLocalMillis ? -1 :
697 (iLocalMillis == other.iLocalMillis ? 0 : 1));
698
699 }
700 }
701 return super.compareTo(partial);
702 }
703
704 //-----------------------------------------------------------------------
705 /**
706 * Converts this object to a DateTime using the default zone.
707 * <p>
708 * This method will throw an exception if the datetime that would be
709 * created does not exist when the time zone is taken into account.
710 *
711 * @return <code>this</code>
712 */
713 public DateTime toDateTime() {
714 return toDateTime((DateTimeZone) null);
715 }
716
717 /**
718 * Converts this object to a DateTime using the specified zone.
719 * <p>
720 * This method will throw an exception if the datetime that would be
721 * created does not exist when the time zone is taken into account.
722 *
723 * @param zone time zone to apply, or default if null
724 * @return a DateTime using the same millis
725 */
726 public DateTime toDateTime(DateTimeZone zone) {
727 zone = DateTimeUtils.getZone(zone);
728 Chronology chrono = iChronology.withZone(zone);
729 return new DateTime(
730 getYear(), getMonthOfYear(), getDayOfMonth(),
731 getHourOfDay(), getMinuteOfHour(),
732 getSecondOfMinute(), getMillisOfSecond(), chrono);
733 }
734
735 //-----------------------------------------------------------------------
736 /**
737 * Converts this object to a LocalDate with the same date and chronology.
738 *
739 * @return a LocalDate with the same date and chronology
740 */
741 public LocalDate toLocalDate() {
742 return new LocalDate(getLocalMillis(), getChronology());
743 }
744
745 /**
746 * Converts this object to a LocalTime with the same time and chronology.
747 *
748 * @return a LocalTime with the same time and chronology
749 */
750 public LocalTime toLocalTime() {
751 return new LocalTime(getLocalMillis(), getChronology());
752 }
753
754 //-----------------------------------------------------------------------
755 /**
756 * Get the date time as a <code>java.util.Date</code>.
757 * <p>
758 * The <code>Date</code> object created has exactly the same fields as this
759 * date-time, except when the time would be invalid due to a daylight savings
760 * gap. In that case, the time will be set to the earliest valid time after the gap.
761 * <p>
762 * In the case of a daylight savings overlap, the earlier instant is selected.
763 * <p>
764 * Converting to a JDK Date is full of complications as the JDK Date constructor
765 * doesn't behave as you might expect around DST transitions. This method works
766 * by taking a first guess and then adjusting. This also handles the situation
767 * where the JDK time zone data differs from the Joda-Time time zone data.
768 *
769 * @return a Date initialised with this date-time, never null
770 * @since 2.0
771 */
772 @SuppressWarnings("deprecation")
773 public Date toDate() {
774 int dom = getDayOfMonth();
775 Date date = new Date(getYear() - 1900, getMonthOfYear() - 1, dom,
776 getHourOfDay(), getMinuteOfHour(), getSecondOfMinute());
777 date.setTime(date.getTime() + getMillisOfSecond());
778 LocalDateTime check = LocalDateTime.fromDateFields(date);
779 if (check.isBefore(this)) {
780 // DST gap
781 // move forward in units of one minute until equal/after
782 while (check.isBefore(this)) {
783 date.setTime(date.getTime() + 60000);
784 check = LocalDateTime.fromDateFields(date);
785 }
786 // move back in units of one second until date wrong
787 while (check.isBefore(this) == false) {
788 date.setTime(date.getTime() - 1000);
789 check = LocalDateTime.fromDateFields(date);
790 }
791 date.setTime(date.getTime() + 1000);
792 } else if (check.equals(this)) {
793 // check for DST overlap
794 Date earlier = new Date(date.getTime() - TimeZone.getDefault().getDSTSavings());
795 check = LocalDateTime.fromDateFields(earlier);
796 if (check.equals(this)) {
797 date = earlier;
798 }
799 }
800 return date;
801 }
802
803 //-----------------------------------------------------------------------
804 /**
805 * Returns a copy of this datetime with different local millis.
806 * <p>
807 * The returned object will be a new instance of the same type.
808 * Only the millis will change, the chronology is kept.
809 * The returned object will be either be a new instance or <code>this</code>.
810 *
811 * @param newMillis the new millis, from 1970-01-01T00:00:00
812 * @return a copy of this datetime with different millis
813 */
814 LocalDateTime withLocalMillis(long newMillis) {
815 return (newMillis == getLocalMillis() ? this : new LocalDateTime(newMillis, getChronology()));
816 }
817
818 //-----------------------------------------------------------------------
819 /**
820 * Returns a copy of this datetime with the specified date,
821 * retaining the time fields.
822 * <p>
823 * If the date is already the date passed in, then <code>this</code> is returned.
824 * <p>
825 * To set a single field use the properties, for example:
826 * <pre>
827 * DateTime set = dt.monthOfYear().setCopy(6);
828 * </pre>
829 *
830 * @param year the new year value
831 * @param monthOfYear the new monthOfYear value
832 * @param dayOfMonth the new dayOfMonth value
833 * @return a copy of this datetime with a different date
834 * @throws IllegalArgumentException if any value if invalid
835 */
836 public LocalDateTime withDate(int year, int monthOfYear, int dayOfMonth) {
837 Chronology chrono = getChronology();
838 long instant = getLocalMillis();
839 instant = chrono.year().set(instant, year);
840 instant = chrono.monthOfYear().set(instant, monthOfYear);
841 instant = chrono.dayOfMonth().set(instant, dayOfMonth);
842 return withLocalMillis(instant);
843 }
844
845 /**
846 * Returns a copy of this datetime with the specified time,
847 * retaining the date fields.
848 * <p>
849 * If the time is already the time passed in, then <code>this</code> is returned.
850 * <p>
851 * To set a single field use the properties, for example:
852 * <pre>
853 * LocalDateTime set = dt.hourOfDay().setCopy(6);
854 * </pre>
855 *
856 * @param hourOfDay the hour of the day
857 * @param minuteOfHour the minute of the hour
858 * @param secondOfMinute the second of the minute
859 * @param millisOfSecond the millisecond of the second
860 * @return a copy of this datetime with a different time
861 * @throws IllegalArgumentException if any value if invalid
862 */
863 public LocalDateTime withTime(int hourOfDay, int minuteOfHour, int secondOfMinute, int millisOfSecond) {
864 Chronology chrono = getChronology();
865 long instant = getLocalMillis();
866 instant = chrono.hourOfDay().set(instant, hourOfDay);
867 instant = chrono.minuteOfHour().set(instant, minuteOfHour);
868 instant = chrono.secondOfMinute().set(instant, secondOfMinute);
869 instant = chrono.millisOfSecond().set(instant, millisOfSecond);
870 return withLocalMillis(instant);
871 }
872
873 //-----------------------------------------------------------------------
874 /**
875 * Returns a copy of this datetime with the partial set of fields
876 * replacing those from this instance.
877 * <p>
878 * For example, if the partial is a <code>TimeOfDay</code> then the time fields
879 * would be changed in the returned instance.
880 * If the partial is null, then <code>this</code> is returned.
881 *
882 * @param partial the partial set of fields to apply to this datetime, null ignored
883 * @return a copy of this datetime with a different set of fields
884 * @throws IllegalArgumentException if any value is invalid
885 */
886 public LocalDateTime withFields(ReadablePartial partial) {
887 if (partial == null) {
888 return this;
889 }
890 return withLocalMillis(getChronology().set(partial, getLocalMillis()));
891 }
892
893 /**
894 * Returns a copy of this datetime with the specified field set to a new value.
895 * <p>
896 * For example, if the field type is <code>hourOfDay</code> then the hour of day
897 * field would be changed in the returned instance.
898 * If the field type is null, then <code>this</code> is returned.
899 * <p>
900 * These three lines are equivalent:
901 * <pre>
902 * LocalDateTime updated = dt.withField(DateTimeFieldType.dayOfMonth(), 6);
903 * LocalDateTime updated = dt.dayOfMonth().setCopy(6);
904 * LocalDateTime updated = dt.property(DateTimeFieldType.dayOfMonth()).setCopy(6);
905 * </pre>
906 *
907 * @param fieldType the field type to set, not null
908 * @param value the value to set
909 * @return a copy of this datetime with the field set
910 * @throws IllegalArgumentException if the value is null or invalid
911 */
912 public LocalDateTime withField(DateTimeFieldType fieldType, int value) {
913 if (fieldType == null) {
914 throw new IllegalArgumentException("Field must not be null");
915 }
916 long instant = fieldType.getField(getChronology()).set(getLocalMillis(), value);
917 return withLocalMillis(instant);
918 }
919
920 /**
921 * Returns a copy of this datetime with the value of the specified
922 * field increased.
923 * <p>
924 * If the addition is zero or the field is null, then <code>this</code> is returned.
925 * <p>
926 * These three lines are equivalent:
927 * <pre>
928 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.years(), 6);
929 * LocalDateTime added = dt.plusYears(6);
930 * LocalDateTime added = dt.plus(Period.years(6));
931 * </pre>
932 *
933 * @param fieldType the field type to add to, not null
934 * @param amount the amount to add
935 * @return a copy of this datetime with the field updated
936 * @throws IllegalArgumentException if the value is null or invalid
937 * @throws ArithmeticException if the result exceeds the internal capacity
938 */
939 public LocalDateTime withFieldAdded(DurationFieldType fieldType, int amount) {
940 if (fieldType == null) {
941 throw new IllegalArgumentException("Field must not be null");
942 }
943 if (amount == 0) {
944 return this;
945 }
946 long instant = fieldType.getField(getChronology()).add(getLocalMillis(), amount);
947 return withLocalMillis(instant);
948 }
949
950 //-----------------------------------------------------------------------
951 /**
952 * Returns a copy of this datetime with the specified duration added.
953 * <p>
954 * If the addition is zero, then <code>this</code> is returned.
955 *
956 * @param durationToAdd the duration to add to this one, null means zero
957 * @param scalar the amount of times to add, such as -1 to subtract once
958 * @return a copy of this datetime with the duration added
959 * @throws ArithmeticException if the result exceeds the internal capacity
960 */
961 public LocalDateTime withDurationAdded(ReadableDuration durationToAdd, int scalar) {
962 if (durationToAdd == null || scalar == 0) {
963 return this;
964 }
965 long instant = getChronology().add(getLocalMillis(), durationToAdd.getMillis(), scalar);
966 return withLocalMillis(instant);
967 }
968
969 /**
970 * Returns a copy of this datetime with the specified period added.
971 * <p>
972 * If the addition is zero, then <code>this</code> is returned.
973 * <p>
974 * This method is typically used to add multiple copies of complex
975 * period instances. Adding one field is best achieved using methods
976 * like {@link #withFieldAdded(DurationFieldType, int)}
977 * or {@link #plusYears(int)}.
978 *
979 * @param period the period to add to this one, null means zero
980 * @param scalar the amount of times to add, such as -1 to subtract once
981 * @return a copy of this datetime with the period added
982 * @throws ArithmeticException if the result exceeds the internal capacity
983 */
984 public LocalDateTime withPeriodAdded(ReadablePeriod period, int scalar) {
985 if (period == null || scalar == 0) {
986 return this;
987 }
988 long instant = getChronology().add(period, getLocalMillis(), scalar);
989 return withLocalMillis(instant);
990 }
991
992 //-----------------------------------------------------------------------
993 /**
994 * Returns a copy of this datetime with the specified duration added.
995 * <p>
996 * If the amount is zero or null, then <code>this</code> is returned.
997 *
998 * @param duration the duration to add to this one, null means zero
999 * @return a copy of this datetime with the duration added
1000 * @throws ArithmeticException if the result exceeds the internal capacity
1001 */
1002 public LocalDateTime plus(ReadableDuration duration) {
1003 return withDurationAdded(duration, 1);
1004 }
1005
1006 /**
1007 * Returns a copy of this datetime with the specified period added.
1008 * <p>
1009 * If the amount is zero or null, then <code>this</code> is returned.
1010 * <p>
1011 * This method is typically used to add complex period instances.
1012 * Adding one field is best achieved using methods
1013 * like {@link #plusYears(int)}.
1014 *
1015 * @param period the period to add to this one, null means zero
1016 * @return a copy of this datetime with the period added
1017 * @throws ArithmeticException if the result exceeds the internal capacity
1018 */
1019 public LocalDateTime plus(ReadablePeriod period) {
1020 return withPeriodAdded(period, 1);
1021 }
1022
1023 //-----------------------------------------------------------------------
1024 /**
1025 * Returns a copy of this datetime plus the specified number of years.
1026 * <p>
1027 * This LocalDateTime instance is immutable and unaffected by this method call.
1028 * <p>
1029 * The following three lines are identical in effect:
1030 * <pre>
1031 * LocalDateTime added = dt.plusYears(6);
1032 * LocalDateTime added = dt.plus(Period.years(6));
1033 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.years(), 6);
1034 * </pre>
1035 *
1036 * @param years the amount of years to add, may be negative
1037 * @return the new LocalDateTime plus the increased years
1038 */
1039 public LocalDateTime plusYears(int years) {
1040 if (years == 0) {
1041 return this;
1042 }
1043 long instant = getChronology().years().add(getLocalMillis(), years);
1044 return withLocalMillis(instant);
1045 }
1046
1047 /**
1048 * Returns a copy of this datetime plus the specified number of months.
1049 * <p>
1050 * This LocalDateTime instance is immutable and unaffected by this method call.
1051 * <p>
1052 * The following three lines are identical in effect:
1053 * <pre>
1054 * LocalDateTime added = dt.plusMonths(6);
1055 * LocalDateTime added = dt.plus(Period.months(6));
1056 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.months(), 6);
1057 * </pre>
1058 *
1059 * @param months the amount of months to add, may be negative
1060 * @return the new LocalDateTime plus the increased months
1061 */
1062 public LocalDateTime plusMonths(int months) {
1063 if (months == 0) {
1064 return this;
1065 }
1066 long instant = getChronology().months().add(getLocalMillis(), months);
1067 return withLocalMillis(instant);
1068 }
1069
1070 /**
1071 * Returns a copy of this datetime plus the specified number of weeks.
1072 * <p>
1073 * This LocalDateTime instance is immutable and unaffected by this method call.
1074 * <p>
1075 * The following three lines are identical in effect:
1076 * <pre>
1077 * LocalDateTime added = dt.plusWeeks(6);
1078 * LocalDateTime added = dt.plus(Period.weeks(6));
1079 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.weeks(), 6);
1080 * </pre>
1081 *
1082 * @param weeks the amount of weeks to add, may be negative
1083 * @return the new LocalDateTime plus the increased weeks
1084 */
1085 public LocalDateTime plusWeeks(int weeks) {
1086 if (weeks == 0) {
1087 return this;
1088 }
1089 long instant = getChronology().weeks().add(getLocalMillis(), weeks);
1090 return withLocalMillis(instant);
1091 }
1092
1093 /**
1094 * Returns a copy of this datetime plus the specified number of days.
1095 * <p>
1096 * This LocalDateTime instance is immutable and unaffected by this method call.
1097 * <p>
1098 * The following three lines are identical in effect:
1099 * <pre>
1100 * LocalDateTime added = dt.plusDays(6);
1101 * LocalDateTime added = dt.plus(Period.days(6));
1102 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.days(), 6);
1103 * </pre>
1104 *
1105 * @param days the amount of days to add, may be negative
1106 * @return the new LocalDateTime plus the increased days
1107 */
1108 public LocalDateTime plusDays(int days) {
1109 if (days == 0) {
1110 return this;
1111 }
1112 long instant = getChronology().days().add(getLocalMillis(), days);
1113 return withLocalMillis(instant);
1114 }
1115
1116 //-----------------------------------------------------------------------
1117 /**
1118 * Returns a copy of this datetime plus the specified number of hours.
1119 * <p>
1120 * This LocalDateTime instance is immutable and unaffected by this method call.
1121 * <p>
1122 * The following three lines are identical in effect:
1123 * <pre>
1124 * LocalDateTime added = dt.plusHours(6);
1125 * LocalDateTime added = dt.plus(Period.hours(6));
1126 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.hours(), 6);
1127 * </pre>
1128 *
1129 * @param hours the amount of hours to add, may be negative
1130 * @return the new LocalDateTime plus the increased hours
1131 */
1132 public LocalDateTime plusHours(int hours) {
1133 if (hours == 0) {
1134 return this;
1135 }
1136 long instant = getChronology().hours().add(getLocalMillis(), hours);
1137 return withLocalMillis(instant);
1138 }
1139
1140 /**
1141 * Returns a copy of this datetime plus the specified number of minutes.
1142 * <p>
1143 * This LocalDateTime instance is immutable and unaffected by this method call.
1144 * <p>
1145 * The following three lines are identical in effect:
1146 * <pre>
1147 * LocalDateTime added = dt.plusMinutes(6);
1148 * LocalDateTime added = dt.plus(Period.minutes(6));
1149 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.minutes(), 6);
1150 * </pre>
1151 *
1152 * @param minutes the amount of minutes to add, may be negative
1153 * @return the new LocalDateTime plus the increased minutes
1154 */
1155 public LocalDateTime plusMinutes(int minutes) {
1156 if (minutes == 0) {
1157 return this;
1158 }
1159 long instant = getChronology().minutes().add(getLocalMillis(), minutes);
1160 return withLocalMillis(instant);
1161 }
1162
1163 /**
1164 * Returns a copy of this datetime plus the specified number of seconds.
1165 * <p>
1166 * This LocalDateTime instance is immutable and unaffected by this method call.
1167 * <p>
1168 * The following three lines are identical in effect:
1169 * <pre>
1170 * LocalDateTime added = dt.plusSeconds(6);
1171 * LocalDateTime added = dt.plus(Period.seconds(6));
1172 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.seconds(), 6);
1173 * </pre>
1174 *
1175 * @param seconds the amount of seconds to add, may be negative
1176 * @return the new LocalDateTime plus the increased seconds
1177 */
1178 public LocalDateTime plusSeconds(int seconds) {
1179 if (seconds == 0) {
1180 return this;
1181 }
1182 long instant = getChronology().seconds().add(getLocalMillis(), seconds);
1183 return withLocalMillis(instant);
1184 }
1185
1186 /**
1187 * Returns a copy of this datetime plus the specified number of millis.
1188 * <p>
1189 * This LocalDateTime instance is immutable and unaffected by this method call.
1190 * <p>
1191 * The following three lines are identical in effect:
1192 * <pre>
1193 * LocalDateTime added = dt.plusMillis(6);
1194 * LocalDateTime added = dt.plus(Period.millis(6));
1195 * LocalDateTime added = dt.withFieldAdded(DurationFieldType.millis(), 6);
1196 * </pre>
1197 *
1198 * @param millis the amount of millis to add, may be negative
1199 * @return the new LocalDateTime plus the increased millis
1200 */
1201 public LocalDateTime plusMillis(int millis) {
1202 if (millis == 0) {
1203 return this;
1204 }
1205 long instant = getChronology().millis().add(getLocalMillis(), millis);
1206 return withLocalMillis(instant);
1207 }
1208
1209 //-----------------------------------------------------------------------
1210 /**
1211 * Returns a copy of this datetime with the specified duration taken away.
1212 * <p>
1213 * If the amount is zero or null, then <code>this</code> is returned.
1214 *
1215 * @param duration the duration to reduce this instant by
1216 * @return a copy of this datetime with the duration taken away
1217 * @throws ArithmeticException if the result exceeds the internal capacity
1218 */
1219 public LocalDateTime minus(ReadableDuration duration) {
1220 return withDurationAdded(duration, -1);
1221 }
1222
1223 /**
1224 * Returns a copy of this datetime with the specified period taken away.
1225 * <p>
1226 * If the amount is zero or null, then <code>this</code> is returned.
1227 * <p>
1228 * This method is typically used to subtract complex period instances.
1229 * Subtracting one field is best achieved using methods
1230 * like {@link #minusYears(int)}.
1231 *
1232 * @param period the period to reduce this instant by
1233 * @return a copy of this datetime with the period taken away
1234 * @throws ArithmeticException if the result exceeds the internal capacity
1235 */
1236 public LocalDateTime minus(ReadablePeriod period) {
1237 return withPeriodAdded(period, -1);
1238 }
1239
1240 //-----------------------------------------------------------------------
1241 /**
1242 * Returns a copy of this datetime minus the specified number of years.
1243 * <p>
1244 * This LocalDateTime instance is immutable and unaffected by this method call.
1245 * <p>
1246 * The following three lines are identical in effect:
1247 * <pre>
1248 * LocalDateTime subtracted = dt.minusYears(6);
1249 * LocalDateTime subtracted = dt.minus(Period.years(6));
1250 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.years(), -6);
1251 * </pre>
1252 *
1253 * @param years the amount of years to subtract, may be negative
1254 * @return the new LocalDateTime minus the increased years
1255 */
1256 public LocalDateTime minusYears(int years) {
1257 if (years == 0) {
1258 return this;
1259 }
1260 long instant = getChronology().years().subtract(getLocalMillis(), years);
1261 return withLocalMillis(instant);
1262 }
1263
1264 /**
1265 * Returns a copy of this datetime minus the specified number of months.
1266 * <p>
1267 * This LocalDateTime instance is immutable and unaffected by this method call.
1268 * <p>
1269 * The following three lines are identical in effect:
1270 * <pre>
1271 * LocalDateTime subtracted = dt.minusMonths(6);
1272 * LocalDateTime subtracted = dt.minus(Period.months(6));
1273 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.months(), -6);
1274 * </pre>
1275 *
1276 * @param months the amount of months to subtract, may be negative
1277 * @return the new LocalDateTime minus the increased months
1278 */
1279 public LocalDateTime minusMonths(int months) {
1280 if (months == 0) {
1281 return this;
1282 }
1283 long instant = getChronology().months().subtract(getLocalMillis(), months);
1284 return withLocalMillis(instant);
1285 }
1286
1287 /**
1288 * Returns a copy of this datetime minus the specified number of weeks.
1289 * <p>
1290 * This LocalDateTime instance is immutable and unaffected by this method call.
1291 * <p>
1292 * The following three lines are identical in effect:
1293 * <pre>
1294 * LocalDateTime subtracted = dt.minusWeeks(6);
1295 * LocalDateTime subtracted = dt.minus(Period.weeks(6));
1296 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.weeks(), -6);
1297 * </pre>
1298 *
1299 * @param weeks the amount of weeks to subtract, may be negative
1300 * @return the new LocalDateTime minus the increased weeks
1301 */
1302 public LocalDateTime minusWeeks(int weeks) {
1303 if (weeks == 0) {
1304 return this;
1305 }
1306 long instant = getChronology().weeks().subtract(getLocalMillis(), weeks);
1307 return withLocalMillis(instant);
1308 }
1309
1310 /**
1311 * Returns a copy of this datetime minus the specified number of days.
1312 * <p>
1313 * This LocalDateTime instance is immutable and unaffected by this method call.
1314 * <p>
1315 * The following three lines are identical in effect:
1316 * <pre>
1317 * LocalDateTime subtracted = dt.minusDays(6);
1318 * LocalDateTime subtracted = dt.minus(Period.days(6));
1319 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.days(), -6);
1320 * </pre>
1321 *
1322 * @param days the amount of days to subtract, may be negative
1323 * @return the new LocalDateTime minus the increased days
1324 */
1325 public LocalDateTime minusDays(int days) {
1326 if (days == 0) {
1327 return this;
1328 }
1329 long instant = getChronology().days().subtract(getLocalMillis(), days);
1330 return withLocalMillis(instant);
1331 }
1332
1333 //-----------------------------------------------------------------------
1334 /**
1335 * Returns a copy of this datetime minus the specified number of hours.
1336 * <p>
1337 * This LocalDateTime instance is immutable and unaffected by this method call.
1338 * <p>
1339 * The following three lines are identical in effect:
1340 * <pre>
1341 * LocalDateTime subtracted = dt.minusHours(6);
1342 * LocalDateTime subtracted = dt.minus(Period.hours(6));
1343 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.hours(), -6);
1344 * </pre>
1345 *
1346 * @param hours the amount of hours to subtract, may be negative
1347 * @return the new LocalDateTime minus the increased hours
1348 */
1349 public LocalDateTime minusHours(int hours) {
1350 if (hours == 0) {
1351 return this;
1352 }
1353 long instant = getChronology().hours().subtract(getLocalMillis(), hours);
1354 return withLocalMillis(instant);
1355 }
1356
1357 /**
1358 * Returns a copy of this datetime minus the specified number of minutes.
1359 * <p>
1360 * This LocalDateTime instance is immutable and unaffected by this method call.
1361 * <p>
1362 * The following three lines are identical in effect:
1363 * <pre>
1364 * LocalDateTime subtracted = dt.minusMinutes(6);
1365 * LocalDateTime subtracted = dt.minus(Period.minutes(6));
1366 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.minutes(), -6);
1367 * </pre>
1368 *
1369 * @param minutes the amount of minutes to subtract, may be negative
1370 * @return the new LocalDateTime minus the increased minutes
1371 */
1372 public LocalDateTime minusMinutes(int minutes) {
1373 if (minutes == 0) {
1374 return this;
1375 }
1376 long instant = getChronology().minutes().subtract(getLocalMillis(), minutes);
1377 return withLocalMillis(instant);
1378 }
1379
1380 /**
1381 * Returns a copy of this datetime minus the specified number of seconds.
1382 * <p>
1383 * This LocalDateTime instance is immutable and unaffected by this method call.
1384 * <p>
1385 * The following three lines are identical in effect:
1386 * <pre>
1387 * LocalDateTime subtracted = dt.minusSeconds(6);
1388 * LocalDateTime subtracted = dt.minus(Period.seconds(6));
1389 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.seconds(), -6);
1390 * </pre>
1391 *
1392 * @param seconds the amount of seconds to subtract, may be negative
1393 * @return the new LocalDateTime minus the increased seconds
1394 */
1395 public LocalDateTime minusSeconds(int seconds) {
1396 if (seconds == 0) {
1397 return this;
1398 }
1399 long instant = getChronology().seconds().subtract(getLocalMillis(), seconds);
1400 return withLocalMillis(instant);
1401 }
1402
1403 /**
1404 * Returns a copy of this datetime minus the specified number of millis.
1405 * <p>
1406 * This LocalDateTime instance is immutable and unaffected by this method call.
1407 * <p>
1408 * The following three lines are identical in effect:
1409 * <pre>
1410 * LocalDateTime subtracted = dt.minusMillis(6);
1411 * LocalDateTime subtracted = dt.minus(Period.millis(6));
1412 * LocalDateTime subtracted = dt.withFieldAdded(DurationFieldType.millis(), -6);
1413 * </pre>
1414 *
1415 * @param millis the amount of millis to subtract, may be negative
1416 * @return the new LocalDateTime minus the increased millis
1417 */
1418 public LocalDateTime minusMillis(int millis) {
1419 if (millis == 0) {
1420 return this;
1421 }
1422 long instant = getChronology().millis().subtract(getLocalMillis(), millis);
1423 return withLocalMillis(instant);
1424 }
1425
1426 //-----------------------------------------------------------------------
1427 /**
1428 * Gets the property object for the specified type, which contains many
1429 * useful methods.
1430 *
1431 * @param fieldType the field type to get the chronology for
1432 * @return the property object
1433 * @throws IllegalArgumentException if the field is null or unsupported
1434 */
1435 public Property property(DateTimeFieldType fieldType) {
1436 if (fieldType == null) {
1437 throw new IllegalArgumentException("The DateTimeFieldType must not be null");
1438 }
1439 if (isSupported(fieldType) == false) {
1440 throw new IllegalArgumentException("Field '" + fieldType + "' is not supported");
1441 }
1442 return new Property(this, fieldType.getField(getChronology()));
1443 }
1444
1445 //-----------------------------------------------------------------------
1446 /**
1447 * Get the era field value.
1448 *
1449 * @return the era
1450 */
1451 public int getEra() {
1452 return getChronology().era().get(getLocalMillis());
1453 }
1454
1455 /**
1456 * Get the year of era field value.
1457 *
1458 * @return the year of era
1459 */
1460 public int getCenturyOfEra() {
1461 return getChronology().centuryOfEra().get(getLocalMillis());
1462 }
1463
1464 /**
1465 * Get the year of era field value.
1466 *
1467 * @return the year of era
1468 */
1469 public int getYearOfEra() {
1470 return getChronology().yearOfEra().get(getLocalMillis());
1471 }
1472
1473 /**
1474 * Get the year of century field value.
1475 *
1476 * @return the year of century
1477 */
1478 public int getYearOfCentury() {
1479 return getChronology().yearOfCentury().get(getLocalMillis());
1480 }
1481
1482 /**
1483 * Get the year field value.
1484 *
1485 * @return the year
1486 */
1487 public int getYear() {
1488 return getChronology().year().get(getLocalMillis());
1489 }
1490
1491 /**
1492 * Get the weekyear field value.
1493 * <p>
1494 * The weekyear is the year that matches with the weekOfWeekyear field.
1495 * In the standard ISO8601 week algorithm, the first week of the year
1496 * is that in which at least 4 days are in the year. As a result of this
1497 * definition, day 1 of the first week may be in the previous year.
1498 * The weekyear allows you to query the effective year for that day.
1499 *
1500 * @return the weekyear
1501 */
1502 public int getWeekyear() {
1503 return getChronology().weekyear().get(getLocalMillis());
1504 }
1505
1506 /**
1507 * Get the month of year field value.
1508 *
1509 * @return the month of year
1510 */
1511 public int getMonthOfYear() {
1512 return getChronology().monthOfYear().get(getLocalMillis());
1513 }
1514
1515 /**
1516 * Get the week of weekyear field value.
1517 * <p>
1518 * This field is associated with the "weekyear" via {@link #getWeekyear()}.
1519 * In the standard ISO8601 week algorithm, the first week of the year
1520 * is that in which at least 4 days are in the year. As a result of this
1521 * definition, day 1 of the first week may be in the previous year.
1522 *
1523 * @return the week of a week based year
1524 */
1525 public int getWeekOfWeekyear() {
1526 return getChronology().weekOfWeekyear().get(getLocalMillis());
1527 }
1528
1529 /**
1530 * Get the day of year field value.
1531 *
1532 * @return the day of year
1533 */
1534 public int getDayOfYear() {
1535 return getChronology().dayOfYear().get(getLocalMillis());
1536 }
1537
1538 /**
1539 * Get the day of month field value.
1540 * <p>
1541 * The values for the day of month are defined in {@link org.joda.time.DateTimeConstants}.
1542 *
1543 * @return the day of month
1544 */
1545 public int getDayOfMonth() {
1546 return getChronology().dayOfMonth().get(getLocalMillis());
1547 }
1548
1549 /**
1550 * Get the day of week field value.
1551 * <p>
1552 * The values for the day of week are defined in {@link org.joda.time.DateTimeConstants}.
1553 *
1554 * @return the day of week
1555 */
1556 public int getDayOfWeek() {
1557 return getChronology().dayOfWeek().get(getLocalMillis());
1558 }
1559
1560 //-----------------------------------------------------------------------
1561 /**
1562 * Get the hour of day field value.
1563 *
1564 * @return the hour of day
1565 */
1566 public int getHourOfDay() {
1567 return getChronology().hourOfDay().get(getLocalMillis());
1568 }
1569
1570 /**
1571 * Get the minute of hour field value.
1572 *
1573 * @return the minute of hour
1574 */
1575 public int getMinuteOfHour() {
1576 return getChronology().minuteOfHour().get(getLocalMillis());
1577 }
1578
1579 /**
1580 * Get the second of minute field value.
1581 *
1582 * @return the second of minute
1583 */
1584 public int getSecondOfMinute() {
1585 return getChronology().secondOfMinute().get(getLocalMillis());
1586 }
1587
1588 /**
1589 * Get the millis of second field value.
1590 *
1591 * @return the millis of second
1592 */
1593 public int getMillisOfSecond() {
1594 return getChronology().millisOfSecond().get(getLocalMillis());
1595 }
1596
1597 /**
1598 * Get the millis of day field value.
1599 *
1600 * @return the millis of day
1601 */
1602 public int getMillisOfDay() {
1603 return getChronology().millisOfDay().get(getLocalMillis());
1604 }
1605
1606 //-----------------------------------------------------------------------
1607 /**
1608 * Returns a copy of this datetime with the era field updated.
1609 * <p>
1610 * LocalDateTime is immutable, so there are no set methods.
1611 * Instead, this method returns a new instance with the value of
1612 * era changed.
1613 *
1614 * @param era the era to set
1615 * @return a copy of this object with the field set
1616 * @throws IllegalArgumentException if the value is invalid
1617 */
1618 public LocalDateTime withEra(int era) {
1619 return withLocalMillis(getChronology().era().set(getLocalMillis(), era));
1620 }
1621
1622 /**
1623 * Returns a copy of this datetime with the century of era field updated.
1624 * <p>
1625 * LocalDateTime is immutable, so there are no set methods.
1626 * Instead, this method returns a new instance with the value of
1627 * century of era changed.
1628 *
1629 * @param centuryOfEra the centurey of era to set
1630 * @return a copy of this object with the field set
1631 * @throws IllegalArgumentException if the value is invalid
1632 */
1633 public LocalDateTime withCenturyOfEra(int centuryOfEra) {
1634 return withLocalMillis(getChronology().centuryOfEra().set(getLocalMillis(), centuryOfEra));
1635 }
1636
1637 /**
1638 * Returns a copy of this datetime with the year of era field updated.
1639 * <p>
1640 * LocalDateTime is immutable, so there are no set methods.
1641 * Instead, this method returns a new instance with the value of
1642 * year of era changed.
1643 *
1644 * @param yearOfEra the year of era to set
1645 * @return a copy of this object with the field set
1646 * @throws IllegalArgumentException if the value is invalid
1647 */
1648 public LocalDateTime withYearOfEra(int yearOfEra) {
1649 return withLocalMillis(getChronology().yearOfEra().set(getLocalMillis(), yearOfEra));
1650 }
1651
1652 /**
1653 * Returns a copy of this datetime with the year of century field updated.
1654 * <p>
1655 * LocalDateTime is immutable, so there are no set methods.
1656 * Instead, this method returns a new instance with the value of
1657 * year of century changed.
1658 *
1659 * @param yearOfCentury the year of century to set
1660 * @return a copy of this object with the field set
1661 * @throws IllegalArgumentException if the value is invalid
1662 */
1663 public LocalDateTime withYearOfCentury(int yearOfCentury) {
1664 return withLocalMillis(getChronology().yearOfCentury().set(getLocalMillis(), yearOfCentury));
1665 }
1666
1667 /**
1668 * Returns a copy of this datetime with the year field updated.
1669 * <p>
1670 * LocalDateTime is immutable, so there are no set methods.
1671 * Instead, this method returns a new instance with the value of
1672 * year changed.
1673 *
1674 * @param year the year to set
1675 * @return a copy of this object with the field set
1676 * @throws IllegalArgumentException if the value is invalid
1677 */
1678 public LocalDateTime withYear(int year) {
1679 return withLocalMillis(getChronology().year().set(getLocalMillis(), year));
1680 }
1681
1682 /**
1683 * Returns a copy of this datetime with the weekyear field updated.
1684 * <p>
1685 * The weekyear is the year that matches with the weekOfWeekyear field.
1686 * In the standard ISO8601 week algorithm, the first week of the year
1687 * is that in which at least 4 days are in the year. As a result of this
1688 * definition, day 1 of the first week may be in the previous year.
1689 * The weekyear allows you to query the effective year for that day.
1690 * <p>
1691 * LocalDateTime is immutable, so there are no set methods.
1692 * Instead, this method returns a new instance with the value of
1693 * weekyear changed.
1694 *
1695 * @param weekyear the weekyear to set
1696 * @return a copy of this object with the field set
1697 * @throws IllegalArgumentException if the value is invalid
1698 */
1699 public LocalDateTime withWeekyear(int weekyear) {
1700 return withLocalMillis(getChronology().weekyear().set(getLocalMillis(), weekyear));
1701 }
1702
1703 /**
1704 * Returns a copy of this datetime with the month of year field updated.
1705 * <p>
1706 * LocalDateTime is immutable, so there are no set methods.
1707 * Instead, this method returns a new instance with the value of
1708 * month of year changed.
1709 *
1710 * @param monthOfYear the month of year to set
1711 * @return a copy of this object with the field set
1712 * @throws IllegalArgumentException if the value is invalid
1713 */
1714 public LocalDateTime withMonthOfYear(int monthOfYear) {
1715 return withLocalMillis(getChronology().monthOfYear().set(getLocalMillis(), monthOfYear));
1716 }
1717
1718 /**
1719 * Returns a copy of this datetime with the week of weekyear field updated.
1720 * <p>
1721 * This field is associated with the "weekyear" via {@link #withWeekyear(int)}.
1722 * In the standard ISO8601 week algorithm, the first week of the year
1723 * is that in which at least 4 days are in the year. As a result of this
1724 * definition, day 1 of the first week may be in the previous year.
1725 * <p>
1726 * LocalDateTime is immutable, so there are no set methods.
1727 * Instead, this method returns a new instance with the value of
1728 * week of weekyear changed.
1729 *
1730 * @param weekOfWeekyear the week of weekyear to set
1731 * @return a copy of this object with the field set
1732 * @throws IllegalArgumentException if the value is invalid
1733 */
1734 public LocalDateTime withWeekOfWeekyear(int weekOfWeekyear) {
1735 return withLocalMillis(getChronology().weekOfWeekyear().set(getLocalMillis(), weekOfWeekyear));
1736 }
1737
1738 /**
1739 * Returns a copy of this datetime with the day of year field updated.
1740 * <p>
1741 * LocalDateTime is immutable, so there are no set methods.
1742 * Instead, this method returns a new instance with the value of
1743 * day of year changed.
1744 *
1745 * @param dayOfYear the day of year to set
1746 * @return a copy of this object with the field set
1747 * @throws IllegalArgumentException if the value is invalid
1748 */
1749 public LocalDateTime withDayOfYear(int dayOfYear) {
1750 return withLocalMillis(getChronology().dayOfYear().set(getLocalMillis(), dayOfYear));
1751 }
1752
1753 /**
1754 * Returns a copy of this datetime with the day of month field updated.
1755 * <p>
1756 * LocalDateTime is immutable, so there are no set methods.
1757 * Instead, this method returns a new instance with the value of
1758 * day of month changed.
1759 *
1760 * @param dayOfMonth the day of month to set
1761 * @return a copy of this object with the field set
1762 * @throws IllegalArgumentException if the value is invalid
1763 */
1764 public LocalDateTime withDayOfMonth(int dayOfMonth) {
1765 return withLocalMillis(getChronology().dayOfMonth().set(getLocalMillis(), dayOfMonth));
1766 }
1767
1768 /**
1769 * Returns a copy of this datetime with the day of week field updated.
1770 * <p>
1771 * LocalDateTime is immutable, so there are no set methods.
1772 * Instead, this method returns a new instance with the value of
1773 * day of week changed.
1774 *
1775 * @param dayOfWeek the day of week to set
1776 * @return a copy of this object with the field set
1777 * @throws IllegalArgumentException if the value is invalid
1778 */
1779 public LocalDateTime withDayOfWeek(int dayOfWeek) {
1780 return withLocalMillis(getChronology().dayOfWeek().set(getLocalMillis(), dayOfWeek));
1781 }
1782
1783 //-----------------------------------------------------------------------
1784 /**
1785 * Returns a copy of this datetime with the hour of day field updated.
1786 * <p>
1787 * LocalDateTime is immutable, so there are no set methods.
1788 * Instead, this method returns a new instance with the value of
1789 * hour of day changed.
1790 *
1791 * @param hour the hour of day to set
1792 * @return a copy of this object with the field set
1793 * @throws IllegalArgumentException if the value is invalid
1794 */
1795 public LocalDateTime withHourOfDay(int hour) {
1796 return withLocalMillis(getChronology().hourOfDay().set(getLocalMillis(), hour));
1797 }
1798
1799 /**
1800 * Returns a copy of this datetime with the minute of hour field updated.
1801 * <p>
1802 * LocalDateTime is immutable, so there are no set methods.
1803 * Instead, this method returns a new instance with the value of
1804 * minute of hour changed.
1805 *
1806 * @param minute the minute of hour to set
1807 * @return a copy of this object with the field set
1808 * @throws IllegalArgumentException if the value is invalid
1809 */
1810 public LocalDateTime withMinuteOfHour(int minute) {
1811 return withLocalMillis(getChronology().minuteOfHour().set(getLocalMillis(), minute));
1812 }
1813
1814 /**
1815 * Returns a copy of this datetime with the second of minute field updated.
1816 * <p>
1817 * LocalDateTime is immutable, so there are no set methods.
1818 * Instead, this method returns a new instance with the value of
1819 * second of minute changed.
1820 *
1821 * @param second the second of minute to set
1822 * @return a copy of this object with the field set
1823 * @throws IllegalArgumentException if the value is invalid
1824 */
1825 public LocalDateTime withSecondOfMinute(int second) {
1826 return withLocalMillis(getChronology().secondOfMinute().set(getLocalMillis(), second));
1827 }
1828
1829 /**
1830 * Returns a copy of this datetime with the millis of second field updated.
1831 * <p>
1832 * LocalDateTime is immutable, so there are no set methods.
1833 * Instead, this method returns a new instance with the value of
1834 * millis of second changed.
1835 *
1836 * @param millis the millis of second to set
1837 * @return a copy of this object with the field set
1838 * @throws IllegalArgumentException if the value is invalid
1839 */
1840 public LocalDateTime withMillisOfSecond(int millis) {
1841 return withLocalMillis(getChronology().millisOfSecond().set(getLocalMillis(), millis));
1842 }
1843
1844 /**
1845 * Returns a copy of this datetime with the millis of day field updated.
1846 * <p>
1847 * LocalDateTime is immutable, so there are no set methods.
1848 * Instead, this method returns a new instance with the value of
1849 * millis of day changed.
1850 *
1851 * @param millis the millis of day to set
1852 * @return a copy of this object with the field set
1853 * @throws IllegalArgumentException if the value is invalid
1854 */
1855 public LocalDateTime withMillisOfDay(int millis) {
1856 return withLocalMillis(getChronology().millisOfDay().set(getLocalMillis(), millis));
1857 }
1858
1859 //-----------------------------------------------------------------------
1860 /**
1861 * Get the era property which provides access to advanced functionality.
1862 *
1863 * @return the era property
1864 */
1865 public Property era() {
1866 return new Property(this, getChronology().era());
1867 }
1868
1869 /**
1870 * Get the century of era property which provides access to advanced functionality.
1871 *
1872 * @return the year of era property
1873 */
1874 public Property centuryOfEra() {
1875 return new Property(this, getChronology().centuryOfEra());
1876 }
1877
1878 /**
1879 * Get the year of century property which provides access to advanced functionality.
1880 *
1881 * @return the year of era property
1882 */
1883 public Property yearOfCentury() {
1884 return new Property(this, getChronology().yearOfCentury());
1885 }
1886
1887 /**
1888 * Get the year of era property which provides access to advanced functionality.
1889 *
1890 * @return the year of era property
1891 */
1892 public Property yearOfEra() {
1893 return new Property(this, getChronology().yearOfEra());
1894 }
1895
1896 /**
1897 * Get the year property which provides access to advanced functionality.
1898 *
1899 * @return the year property
1900 */
1901 public Property year() {
1902 return new Property(this, getChronology().year());
1903 }
1904
1905 /**
1906 * Get the weekyear property which provides access to advanced functionality.
1907 *
1908 * @return the weekyear property
1909 */
1910 public Property weekyear() {
1911 return new Property(this, getChronology().weekyear());
1912 }
1913
1914 /**
1915 * Get the month of year property which provides access to advanced functionality.
1916 *
1917 * @return the month of year property
1918 */
1919 public Property monthOfYear() {
1920 return new Property(this, getChronology().monthOfYear());
1921 }
1922
1923 /**
1924 * Get the week of a week based year property which provides access to advanced functionality.
1925 *
1926 * @return the week of a week based year property
1927 */
1928 public Property weekOfWeekyear() {
1929 return new Property(this, getChronology().weekOfWeekyear());
1930 }
1931
1932 /**
1933 * Get the day of year property which provides access to advanced functionality.
1934 *
1935 * @return the day of year property
1936 */
1937 public Property dayOfYear() {
1938 return new Property(this, getChronology().dayOfYear());
1939 }
1940
1941 /**
1942 * Get the day of month property which provides access to advanced functionality.
1943 *
1944 * @return the day of month property
1945 */
1946 public Property dayOfMonth() {
1947 return new Property(this, getChronology().dayOfMonth());
1948 }
1949
1950 /**
1951 * Get the day of week property which provides access to advanced functionality.
1952 *
1953 * @return the day of week property
1954 */
1955 public Property dayOfWeek() {
1956 return new Property(this, getChronology().dayOfWeek());
1957 }
1958
1959 //-----------------------------------------------------------------------
1960 /**
1961 * Get the hour of day field property which provides access to advanced functionality.
1962 *
1963 * @return the hour of day property
1964 */
1965 public Property hourOfDay() {
1966 return new Property(this, getChronology().hourOfDay());
1967 }
1968
1969 /**
1970 * Get the minute of hour field property which provides access to advanced functionality.
1971 *
1972 * @return the minute of hour property
1973 */
1974 public Property minuteOfHour() {
1975 return new Property(this, getChronology().minuteOfHour());
1976 }
1977
1978 /**
1979 * Get the second of minute field property which provides access to advanced functionality.
1980 *
1981 * @return the second of minute property
1982 */
1983 public Property secondOfMinute() {
1984 return new Property(this, getChronology().secondOfMinute());
1985 }
1986
1987 /**
1988 * Get the millis of second property which provides access to advanced functionality.
1989 *
1990 * @return the millis of second property
1991 */
1992 public Property millisOfSecond() {
1993 return new Property(this, getChronology().millisOfSecond());
1994 }
1995
1996 /**
1997 * Get the millis of day property which provides access to advanced functionality.
1998 *
1999 * @return the millis of day property
2000 */
2001 public Property millisOfDay() {
2002 return new Property(this, getChronology().millisOfDay());
2003 }
2004
2005 //-----------------------------------------------------------------------
2006 /**
2007 * Output the date time in ISO8601 format (yyyy-MM-ddTHH:mm:ss.SSS).
2008 *
2009 * @return ISO8601 time formatted string.
2010 */
2011 @ToString
2012 public String toString() {
2013 return ISODateTimeFormat.dateTime().print(this);
2014 }
2015
2016 /**
2017 * Output the date using the specified format pattern.
2018 *
2019 * @param pattern the pattern specification, null means use <code>toString</code>
2020 * @see org.joda.time.format.DateTimeFormat
2021 */
2022 public String toString(String pattern) {
2023 if (pattern == null) {
2024 return toString();
2025 }
2026 return DateTimeFormat.forPattern(pattern).print(this);
2027 }
2028
2029 /**
2030 * Output the date using the specified format pattern.
2031 *
2032 * @param pattern the pattern specification, null means use <code>toString</code>
2033 * @param locale Locale to use, null means default
2034 * @see org.joda.time.format.DateTimeFormat
2035 */
2036 public String toString(String pattern, Locale locale) throws IllegalArgumentException {
2037 if (pattern == null) {
2038 return toString();
2039 }
2040 return DateTimeFormat.forPattern(pattern).withLocale(locale).print(this);
2041 }
2042
2043 //-----------------------------------------------------------------------
2044 /**
2045 * LocalDateTime.Property binds a LocalDateTime to a DateTimeField allowing
2046 * powerful datetime functionality to be easily accessed.
2047 * <p>
2048 * The simplest use of this class is as an alternative get method, here used to
2049 * get the year '1972' (as an int) and the month 'December' (as a String).
2050 * <pre>
2051 * LocalDateTime dt = new LocalDateTime(1972, 12, 3, 0, 0);
2052 * int year = dt.year().get();
2053 * String monthStr = dt.month().getAsText();
2054 * </pre>
2055 * <p>
2056 * Methods are also provided that allow date modification. These return
2057 * new instances of LocalDateTime - they do not modify the original.
2058 * The example below yields two independent immutable date objects
2059 * 20 years apart.
2060 * <pre>
2061 * LocalDateTime dt = new LocalDateTime(1972, 12, 3, 0, 0);
2062 * LocalDateTime dt1920 = dt.year().setCopy(1920);
2063 * </pre>
2064 * <p>
2065 * LocalDateTime.Property itself is thread-safe and immutable, as well as the
2066 * LocalDateTime being operated on.
2067 *
2068 * @author Stephen Colebourne
2069 * @author Brian S O'Neill
2070 * @since 1.3
2071 */
2072 public static final class Property extends AbstractReadableInstantFieldProperty {
2073
2074 /** Serialization version */
2075 private static final long serialVersionUID = -358138762846288L;
2076
2077 /** The instant this property is working against */
2078 private transient LocalDateTime iInstant;
2079 /** The field this property is working against */
2080 private transient DateTimeField iField;
2081
2082 /**
2083 * Constructor.
2084 *
2085 * @param instant the instant to set
2086 * @param field the field to use
2087 */
2088 Property(LocalDateTime instant, DateTimeField field) {
2089 super();
2090 iInstant = instant;
2091 iField = field;
2092 }
2093
2094 /**
2095 * Writes the property in a safe serialization format.
2096 */
2097 private void writeObject(ObjectOutputStream oos) throws IOException {
2098 oos.writeObject(iInstant);
2099 oos.writeObject(iField.getType());
2100 }
2101
2102 /**
2103 * Reads the property from a safe serialization format.
2104 */
2105 private void readObject(ObjectInputStream oos) throws IOException, ClassNotFoundException {
2106 iInstant = (LocalDateTime) oos.readObject();
2107 DateTimeFieldType type = (DateTimeFieldType) oos.readObject();
2108 iField = type.getField(iInstant.getChronology());
2109 }
2110
2111 //-----------------------------------------------------------------------
2112 /**
2113 * Gets the field being used.
2114 *
2115 * @return the field
2116 */
2117 public DateTimeField getField() {
2118 return iField;
2119 }
2120
2121 /**
2122 * Gets the milliseconds of the datetime that this property is linked to.
2123 *
2124 * @return the milliseconds
2125 */
2126 protected long getMillis() {
2127 return iInstant.getLocalMillis();
2128 }
2129
2130 /**
2131 * Gets the chronology of the datetime that this property is linked to.
2132 *
2133 * @return the chronology
2134 * @since 1.4
2135 */
2136 protected Chronology getChronology() {
2137 return iInstant.getChronology();
2138 }
2139
2140 /**
2141 * Gets the LocalDateTime object linked to this property.
2142 *
2143 * @return the linked LocalDateTime
2144 */
2145 public LocalDateTime getLocalDateTime() {
2146 return iInstant;
2147 }
2148
2149 //-----------------------------------------------------------------------
2150 /**
2151 * Adds to this field in a copy of this LocalDateTime.
2152 * <p>
2153 * The LocalDateTime attached to this property is unchanged by this call.
2154 *
2155 * @param value the value to add to the field in the copy
2156 * @return a copy of the LocalDateTime with the field value changed
2157 * @throws IllegalArgumentException if the value isn't valid
2158 */
2159 public LocalDateTime addToCopy(int value) {
2160 return iInstant.withLocalMillis(iField.add(iInstant.getLocalMillis(), value));
2161 }
2162
2163 /**
2164 * Adds to this field in a copy of this LocalDateTime.
2165 * <p>
2166 * The LocalDateTime attached to this property is unchanged by this call.
2167 *
2168 * @param value the value to add to the field in the copy
2169 * @return a copy of the LocalDateTime with the field value changed
2170 * @throws IllegalArgumentException if the value isn't valid
2171 */
2172 public LocalDateTime addToCopy(long value) {
2173 return iInstant.withLocalMillis(iField.add(iInstant.getLocalMillis(), value));
2174 }
2175
2176 /**
2177 * Adds to this field, possibly wrapped, in a copy of this LocalDateTime.
2178 * A field wrapped operation only changes this field.
2179 * Thus 31st January addWrapField one day goes to the 1st January.
2180 * <p>
2181 * The LocalDateTime attached to this property is unchanged by this call.
2182 *
2183 * @param value the value to add to the field in the copy
2184 * @return a copy of the LocalDateTime with the field value changed
2185 * @throws IllegalArgumentException if the value isn't valid
2186 */
2187 public LocalDateTime addWrapFieldToCopy(int value) {
2188 return iInstant.withLocalMillis(iField.addWrapField(iInstant.getLocalMillis(), value));
2189 }
2190
2191 //-----------------------------------------------------------------------
2192 /**
2193 * Sets this field in a copy of the LocalDateTime.
2194 * <p>
2195 * The LocalDateTime attached to this property is unchanged by this call.
2196 *
2197 * @param value the value to set the field in the copy to
2198 * @return a copy of the LocalDateTime with the field value changed
2199 * @throws IllegalArgumentException if the value isn't valid
2200 */
2201 public LocalDateTime setCopy(int value) {
2202 return iInstant.withLocalMillis(iField.set(iInstant.getLocalMillis(), value));
2203 }
2204
2205 /**
2206 * Sets this field in a copy of the LocalDateTime to a parsed text value.
2207 * <p>
2208 * The LocalDateTime attached to this property is unchanged by this call.
2209 *
2210 * @param text the text value to set
2211 * @param locale optional locale to use for selecting a text symbol
2212 * @return a copy of the LocalDateTime with the field value changed
2213 * @throws IllegalArgumentException if the text value isn't valid
2214 */
2215 public LocalDateTime setCopy(String text, Locale locale) {
2216 return iInstant.withLocalMillis(iField.set(iInstant.getLocalMillis(), text, locale));
2217 }
2218
2219 /**
2220 * Sets this field in a copy of the LocalDateTime to a parsed text value.
2221 * <p>
2222 * The LocalDateTime attached to this property is unchanged by this call.
2223 *
2224 * @param text the text value to set
2225 * @return a copy of the LocalDateTime with the field value changed
2226 * @throws IllegalArgumentException if the text value isn't valid
2227 */
2228 public LocalDateTime setCopy(String text) {
2229 return setCopy(text, null);
2230 }
2231
2232 //-----------------------------------------------------------------------
2233 /**
2234 * Returns a new LocalDateTime with this field set to the maximum value
2235 * for this field.
2236 * <p>
2237 * This operation is useful for obtaining a LocalDateTime on the last day
2238 * of the month, as month lengths vary.
2239 * <pre>
2240 * LocalDateTime lastDayOfMonth = dt.dayOfMonth().withMaximumValue();
2241 * </pre>
2242 * <p>
2243 * The LocalDateTime attached to this property is unchanged by this call.
2244 *
2245 * @return a copy of the LocalDateTime with this field set to its maximum
2246 */
2247 public LocalDateTime withMaximumValue() {
2248 return setCopy(getMaximumValue());
2249 }
2250
2251 /**
2252 * Returns a new LocalDateTime with this field set to the minimum value
2253 * for this field.
2254 * <p>
2255 * The LocalDateTime attached to this property is unchanged by this call.
2256 *
2257 * @return a copy of the LocalDateTime with this field set to its minimum
2258 */
2259 public LocalDateTime withMinimumValue() {
2260 return setCopy(getMinimumValue());
2261 }
2262
2263 //-----------------------------------------------------------------------
2264 /**
2265 * Rounds to the lowest whole unit of this field on a copy of this
2266 * LocalDateTime.
2267 * <p>
2268 * For example, rounding floor on the hourOfDay field of a LocalDateTime
2269 * where the time is 10:30 would result in new LocalDateTime with the
2270 * time of 10:00.
2271 *
2272 * @return a copy of the LocalDateTime with the field value changed
2273 */
2274 public LocalDateTime roundFloorCopy() {
2275 return iInstant.withLocalMillis(iField.roundFloor(iInstant.getLocalMillis()));
2276 }
2277
2278 /**
2279 * Rounds to the highest whole unit of this field on a copy of this
2280 * LocalDateTime.
2281 * <p>
2282 * For example, rounding floor on the hourOfDay field of a LocalDateTime
2283 * where the time is 10:30 would result in new LocalDateTime with the
2284 * time of 11:00.
2285 *
2286 * @return a copy of the LocalDateTime with the field value changed
2287 */
2288 public LocalDateTime roundCeilingCopy() {
2289 return iInstant.withLocalMillis(iField.roundCeiling(iInstant.getLocalMillis()));
2290 }
2291
2292 /**
2293 * Rounds to the nearest whole unit of this field on a copy of this
2294 * LocalDateTime, favoring the floor if halfway.
2295 *
2296 * @return a copy of the LocalDateTime with the field value changed
2297 */
2298 public LocalDateTime roundHalfFloorCopy() {
2299 return iInstant.withLocalMillis(iField.roundHalfFloor(iInstant.getLocalMillis()));
2300 }
2301
2302 /**
2303 * Rounds to the nearest whole unit of this field on a copy of this
2304 * LocalDateTime, favoring the ceiling if halfway.
2305 *
2306 * @return a copy of the LocalDateTime with the field value changed
2307 */
2308 public LocalDateTime roundHalfCeilingCopy() {
2309 return iInstant.withLocalMillis(iField.roundHalfCeiling(iInstant.getLocalMillis()));
2310 }
2311
2312 /**
2313 * Rounds to the nearest whole unit of this field on a copy of this
2314 * LocalDateTime. If halfway, the ceiling is favored over the floor
2315 * only if it makes this field's value even.
2316 *
2317 * @return a copy of the LocalDateTime with the field value changed
2318 */
2319 public LocalDateTime roundHalfEvenCopy() {
2320 return iInstant.withLocalMillis(iField.roundHalfEven(iInstant.getLocalMillis()));
2321 }
2322 }
2323
2324 }