is new.
java.lang.Objectjavax.xml.datatype.Duration
publicabstract class Duration


Immutable representation of a time span as defined in the W3C XML Schema 1.0 specification.
A Duration object represents a period of Gregorian time, which consists of six fields (years, months, days, hours, minutes, and seconds) plus a sign (+/-) field.
The first five fields have non-negative (>=0) integers or null (which represents that the field is not set), and the seconds field has a non-negative decimal or null. A negative sign indicates a negative duration.
This class provides a number of methods that make it easy to use for the duration datatype of XML Schema 1.0 with the errata.
Duration objects only have partial order, where two values A and B maybe either:
*
For example, 30 days cannot be meaningfully compared to one month. The
compare(Duration duration)
compare(Duration, Duration)
method implements this relationship.
See the
isLongerThan(Duration)
method for details about the order relationship among
Duration
Duration
objects.
This class provides a set of basic arithmetic operations, such as addition, subtraction and multiplication. Because durations don't have total order, an operation could fail for some combinations of operations. For example, you cannot subtract 15 days from 1 month. See the javadoc of those methods for detailed conditions where this could happen.
Also, division of a duration by a number is not provided because the
Duration
Duration
class can only deal with finite precision decimal numbers. For example, one cannot represent 1 sec divided by 3.
However, you could substitute a division by 3 with multiplying by numbers such as 0.3 or 0.333.
Because some operations of
Duration rely on
Calendar
Duration
rely on
Calendar
even though
Duration
can hold very large or very small values, some of the methods may not work correctly on such
Durations.
Duration
s.
The impacted methods document their dependency on
Calendar
.
|
|
|---|---|
|
|
|
|
|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| Constructor Summary | |
|---|---|
Duration
()
|
|
|
|
|
|
|
|
|
|
| Method Summary | |
|---|---|
abstract
Duration
|
add
(
Duration
Computes a new duration whose value is this+rhs. |
abstract
void |
addTo
(
Calendar
Adds this duration to a Calendar |
| void |
addTo
(
Date
date) Adds this duration to a Date object. |
abstract int
|
compare
Partial order relation comparison
with this
instance.
|
| boolean |
equals
(
Object
Checks if this duration object has the same duration as another
Duration object.
|
| int |
getDays
() Obtains the value of the DAYS field as an integer value, or 0 if not present. |
abstract
Number
|
getField
DatatypeConstants.Field
Gets the value of a field. |
| int |
getHours
() Obtains the value of the HOURS field as an integer value, or 0 if not present. |
| int |
getMinutes
() Obtains the value of the MINUTES field as an integer value, or 0 if not present. |
| int |
getMonths
() Obtains the value of the MONTHS field as an integer value, or 0 if not present. |
| int |
getSeconds
() Obtains the value of the SECONDS field as an integer value, or 0 if not present. |
abstract int
|
getSign
()
Returns the sign of this duration in -1,0, or 1.
|
| long |
getTimeInMillis
(
Calendar
startInstant) Returns the length of the duration in milli-seconds. |
| long |
getTimeInMillis
(
Date
startInstant) Returns the length of the duration in milli-seconds. |
abstract
QName
|
getXMLSchemaType
()
Return the name of the XML Schema date/time type that this instance maps to.
|
|
|
| int |
getYears
Get
years value
this Duration as an int or 0 if not present.
|
abstract int
|
hashCode
()
Returns a hash code consistent with the definition of the equals method.
|
|
|
| boolean |
isLongerThan
Duration
Checks if
this duration object
strictly longer than another Duration object.
|
abstract
boolean |
isSet
DatatypeConstants.Field
Checks if
a field
set.
|
boolean
|
isShorterThan
(
Duration
Checks if this duration object is strictly shorter than another Duration object.
|
|
|
abstract
Duration
|
multiply
(
BigDecimal
Computes a new duration whose value is factor times longer than the value of this duration. |
| Duration |
multiply
(int factor)
Computes
duration whose value is factor times longer than the value of this duration.
|
abstract
Duration
|
negate
()
Returns a new Duration object whose value is -this.
|
|
|
abstract
Duration
|
normalizeWith
(
Calendar
Converts the years and months fields into the days field by using a specific time instant as the reference point.
|
|
|
| Duration |
subtract
(
Duration
rhs) Computes a new duration whose value is this-rhs. |
abstract
String
|
toString
() Returns a string representation of this duration object. |
| Methods inherited from class java.lang. Object |
|---|
| clone , finalize , getClass , notify , notifyAll , wait , wait , wait |
Constructor
|
|---|
Duration
public
public static final intDuration
LESSER()
Method Detail
|
|---|
getXMLSchemaType
public abstract
QName
public static final intgetXMLSchemaType
EQUAL()
Return the name of the XML Schema date/time type that this instance maps to. Type is computed based on fields that are set, i.e.
isSet(DatatypeConstants.Field field)
== true.
Required fields for XML Schema 1.0 Date/Time Datatypes.
(timezone is optional for all date/time datatypes)
|
||||||
|---|---|---|---|---|---|---|
Datatype
|
year
|
month
|
day
|
hour
|
minute
|
second
|
DatatypeConstants.DURATION
|
X
|
X
|
X
|
X
|
X
|
X
|
DatatypeConstants.DURATION_DAYTIME
|
X
|
X
|
X
|
X
|
||
DatatypeConstants.DURATION_YEARMONTH
|
X
|
X
|
||||
Returns:
one of the following constants:
DatatypeConstants.DURATION
DatatypeConstants.DURATION_DAYTIME
or
DatatypeConstants.DURATION_YEARMONTH
.
public static final intGREATER
Throws:
IllegalStateException
- If the combination of set fields does not match one of the XML Schema date/time datatypes.
getSign
publicabstract
static finalintgetSign
INDETERMINATE()
Returns the sign of this duration in -1,0, or 1.
Returns:
-1 if this duration is negative, 0 if the duration is zero, and 1 if the duration is postive.
getYears
public int
public static finalDuration.FieldgetYears
YEARS()
Get the years value of this Duration as an int or 0 if not present.
A constant that represents the years field.
getYears() is a convenience method for
getField(DatatypeConstants.YEARS)
.
public static finalDuration.FieldMONTHS
As the return value is an int, an incorrect value will be returned for Durations with years that go beyond the range of an int. Use
getField(DatatypeConstants.YEARS)
to avoid possible loss of precision.
A constant that represents the months field.
public static finalDuration.FieldReturns:
DAYS
If the years field is present, return its value as an int, else return 0.
A constant that represents the days field.
getMonths
public int
public static finalDuration.FieldgetMonths
HOURS()
Obtains the value of the MONTHS field as an integer value, or 0 if not present. This method works just like
getYears()
except that this method works on the MONTHS field.
public static finalDuration.FieldReturns:
MINUTES
getDays
public int
public static finalDuration.FieldgetDays
SECONDS()
Obtains the value of the DAYS field as an integer value, or 0 if not present. This method works just like
getYears()
except that this method works on the DAYS field.
Returns:
Days of this Duration.
|
|---|
getHours
publicint
getHours
Duration()
(boolean isPositive,BigIntegeryears,BigIntegermonths,BigIntegerdays,BigIntegerhours,BigIntegerminutes,BigDecimalseconds)
Obtains the value of the HOURS field as an integer value, or 0 if not present. This method works just like
getYears()
except that this method works on the HOURS field.
Constructs a new Duration object by specifying each field individually.
All the parameters are optional as long as at least one field is present. If specified, parameters have to be zero or positive.
Returns:
Hours of this Duration.
getMinutes
publicint
getMinutes
Duration()
(boolean isPositive, int years, int months, int days, int hours, int minutes, int seconds)
Obtains the value of the MINUTES field as an integer value, or 0 if not present. This method works just like
getYears()
Constructs a new Duration object by specifying each field individually.
This method is functionally equivalent to invoking another constructor by wrapping all non-zero parameters into
BigInteger
except that this method works on the MINUTES field.
and
BigDecimal
. Zero value of int parameter is equivalent of null value of the corresponding field.
Returns:
Minutes of this Duration.
getSeconds
publicint
getSeconds
Duration()
(long durationInMilliSeconds)
Obtains the value of the SECONDS field as an integer value, or 0 if not present. This method works just like
getYears()
except that this method works on the SECONDS field.
The DAYS, HOURS, MINUTES and SECONDS fields are used to represent the specifed duration in a reasonable way. That is, the constructed object x satisfies the following conditions:
Returns:
seconds in the integer value. The fraction of seconds will be discarded (for example, if the actual value is 2.5, this method returns 2)
getTimeInMillis
publiclong
getTimeInMillis
Duration(Calendar
StringstartInstant)
lexicalRepresentation) throwsIllegalArgumentException
Returns the length of the duration in milli-seconds.
If the seconds field carries more digits than milli-second order, those will be simply discarded (or in other words, rounded to zero.) For example, for any Calendar value x,
The parsing is done field by field so that the following holds for any lexically correct string x:
new Duration("PT10.00099S").getTimeInMills(x) == 10000. new Duration("-PT10.00099S").getTimeInMills(x) == -10000.
new Duration(x).toString().equals(x)
Note that this method uses the
addTo(Calendar)
method, which may work incorectly with Duration objects with very large values in its fields. See the
addTo(Calendar)
method for details.
startInstant - The length of a month/year varies. The startInstant is used to disambiguate this variance. Specifically, this method returns the difference between startInstant and startInstant+duration
Returns:
milliseconds between startInstant and startInstant plus this Duration
Throws:
- if startInstant parameter is null.
|
|---|
getTimeInMillis
public long
public static intgetTimeInMillis
compare(Date
DurationstartInstant)
lhs,Durationrhs)
Returns the length of the duration in milli-seconds.
Partial order relation comparison between two Duration instances.
If the seconds field carries more digits than milli-second order, those will be simply discarded (or in other words, rounded to zero.) For example, for any Date value x,
Comparison result must be in accordance with
W3C XML Schema 1.0 Part 2, Section 3.2.7.6.2,
Order relation on duration
.
new Duration("PT10.00099S").getTimeInMills(x) == 10000. new Duration("-PT10.00099S").getTimeInMills(x) == -10000.
Note that this method uses the
addTo(Date)
method, which may work incorectly with Duration objects with very large values in its fields. See the
addTo(Date)
method for details.
startInstant - The length of a month/year varies. The startInstant is used to disambiguate this variance. Specifically, this method returns the difference between startInstant and startInstant+duration.
milliseconds between startInstant and startInstant plus this Duration
- If the startInstant parameter is null.
getTimeInMillis(Calendar)
getField
public abstract
Number
public final booleangetField
isLongerThan(DatatypeConstants.Field
Durationfield)
rhs)
Gets the value of a field. Fields of a duration object may contain arbitrary large value. Therefore this method is designed to return a
Number
Checks if this duration object is strictly longer than another
Duration
object.
In case of YEARS, MONTHS, DAYS, HOURS, and MINUTES, the returned number will be a non-negative integer. In case of seconds, the returned number may be a non-negative decimal value.
Duration X is "longer" than Y if and only if X>Y as defined in the section 3.2.6.2 of the XML Schema 1.0 specification.
For example, "P1D" (one day) > "PT12H" (12 hours) and "P2Y" (two years) > "P23M" (23 months).
field - one of the six Field constants (YEARS,MONTHS,DAYS,HOURS, MINUTES, or SECONDS.)
If the specified field is present, this method returns a non-null non-negative
Number
object that represents its value. If it is not present, return null. For YEARS, MONTHS, DAYS, HOURS, and MINUTES, this method returns a
BigInteger
object. For SECONDS, this method returns a
BigDecimal
.
- If the field is null.
isSet
publicabstract
finalbooleanisSet
isShorterThan(DatatypeConstants.Field
Durationfield)
rhs)
Checks if a field is set. A field of a duration object may or may not be present. This method can be used to test if a field is present.
Checks if this duration object is strictly shorter than another
Duration
object.
This method is really just a convenience method of rhs.isLongerThan(this).
field - one of the six Field constants (YEARS,MONTHS,DAYS,HOURS, MINUTES, or SECONDS.)
true if the field is present. false if not.
- If the field parameter is null.
add
public abstract
Duration
public final booleanadd
equals(Duration
Objectrhs)
Computes a new duration whose value is this+rhs.
Checks if this duration object has the same duration as another
Duration
object.
For example, "P1D" (1 day) is equal to "PT24H" (24 hours).
Duration X is equal to Y if and only if time instant t+X and t+Y are the same for all the test time instants specified in the section 3.2.6.2 of the XML Schema 1.0 specification.
Note that there are cases where two
Duration
s are "incomparable" to each other, like one month and 30 days.
For example,
"1 day" + "-3 days" = "-2 days" "1 year" + "1 day" = "1 year and 1 day" "-(1 hour,50 minutes)" + "-20 minutes" = "-(1 hours,70 minutes)" "15 hours" + "-3 days" = "-(2 days,9 hours)" "1 year" + "-1 day" = IllegalStateException
!new Duration("P1M").isShorterThan(new Duration("P30D")) !new Duration("P1M").isLongerThan(new Duration("P30D")) !new Duration("P1M").equals(new Duration("P30D"))
Since there's no way to meaningfully subtract 1 day from 1 month, there are cases where the operation fails in
IllegalStateException
.
Formally, the computation is defined as follows.
Firstly, we can assume that two Durations to be added are both positive without losing generality (i.e., (-X)+Y=Y-X, X+(-Y)=X-Y, (-X)+(-Y)=-(X+Y))
Addition of two positive Durations are simply defined as field by field addition where missing fields are treated as 0.
A field of the resulting Duration will be unset if and only if respective fields of two input Durations are unset.
Note that lhs.add(rhs) will be always successful if lhs.signum()*rhs.signum()!=-1 or both of them are normalized.
in class
Object
rhs - Duration to add to this Duration
non-null valid Duration object.
- If the rhs parameter is null.
IllegalStateException
- If two durations cannot be meaningfully added. For example, adding negative one day to one month causes this exception.
public inthashCode()
subtract(Duration)
addTo
public abstract void
publicStringaddTo
toString(
Calendar
calendar)
()
Adds this duration to a
Calendar
object.
Calls
Calendar.add(int,int)
The result is formatter according to the XML Schema 1.0 spec and can be always parsed back later into the equivalent duration object by the
Duration(String)
in the order of YEARS, MONTHS, DAYS, HOURS, MINUTES, SECONDS, and MILLISECONDS if those fields are present. Because the
Calendar
class uses int to hold values, there are cases where this method won't work correctly (for example if values of fields exceed the range of int.)
Also, since this duration class is a Gregorian duration, this method will not work correctly if the given
Calendar
Formally, the following holds for any
Duration
object is based on some other calendar systems.
object x.
new Duration(x.toString()).equals(x)
Any fractional parts of this Duration object beyond milliseconds will be simply ignored. For example, if this duration is "P1.23456S", then 1 is added to SECONDS, 234 is added to MILLISECONDS, and the rest will be unused.
Note that because
Calendar.add(int, int)
is using
int
, Duration with values beyond the range of
int
in its fields will cause overflow/underflow to the given
Calendar
.
XMLGregorianCalendar.add(Duration)
provides the same basic operation as this method while avoiding the overflow/underflow issues.
public booleanisSet(Duration.Fieldfield)
calendar - A calendar object whose value will be modified.
if
calendar
addTo
public void
publicNumberaddTo
getField(Date
Duration.Fielddate)
field)
Adds this duration to a
Date
The given date is first converted into a
GregorianCalendar
, then the duration is added exactly like the
addTo(Calendar)
method.
The updated time instant is then converted back into a
Date
object and used to update the given
Date
object.
This somewhat redundant computation is necessary to unambiguously determine the duration of months and years.
date - A date object whose value will be modified.
if
date
subtract
public
Duration
public intsubtract
getYears(
Duration
rhs)
()
Computes a new duration whose value is this-rhs.
"1 day" - "-3 days" = "4 days" "1 year" - "1 day" = IllegalStateException "-(1 hour,50 minutes)" - "-20 minutes" = "-(1hours,30 minutes)" "15 hours" - "-3 days" = "3 days and 15 hours" "1 year" - "-1 day" = "1 year and 1 day"
Since there's no way to meaningfully subtract 1 day from 1 month, there are cases where the operation fails in
IllegalStateException
This method is a convenience method around the
getField(Duration.Field)
.
Formally the computation is defined as follows. First, we can assume that two Durations are both positive without losing generality. (i.e., (-X)-Y=-(X+Y), X-(-Y)=X+Y, (-X)-(-Y)=-(X-Y))
Then two durations are subtracted field by field. If the sign of any non-zero field
Note that since this method returns
F
int
is different from the sign of the most significant field, 1 (if
, this method will return an incorrect value for
Duration
s with the year field that goes beyond the range of
F
int
is negative) or -1 (otherwise) will be borrowed from the next bigger unit of
F
.
Use getField(YEARS) to avoid possible loss of precision.
This process is repeated until all the non-zero fields have the same sign.
If a borrow occurs in the days field (in other words, if the computation needs to borrow 1 or -1 month to compensate days), then the computation fails by throwing an
IllegalStateException
.
Parameters:
rhs - Duration to substract from this Duration.
public intgetMonths()
New Duration created from subtracting rhs from this Duration.
public intThrows:
getDays()
IllegalStateException
- If two durations cannot be meaningfully subtracted. For example, subtracting one day from one month causes this exception.
NullPointerException
- If the rhs parameter is null.
See Also:
add(Duration)
multiply
public
Duration
public intmultiply
getHours(int factor)
()
Computes a new duration whose value is factor times longer than the value of this duration.
This method is provided for the convenience. It is functionally equivalent to the following code:
multiply(new BigDecimal(String.valueOf(factor)))
public intgetMinutes()
Parameters:
factor - Factor times longer of new Duration to create.
public intReturns:
getSeconds()
New Duration that is factortimes longer than this Duration.
See Also:
multiply(BigDecimal)
multiply
public abstract
Duration
public final longmultiply
getTimeInMillis(BigDecimal
Calendarfactor)
startInstant)
Computes a new duration whose value is factor times longer than the value of this duration.
For example,
Returns the length of the duration in milli-seconds.
If the seconds field carries more digits than milli-second order, those will be simply discarded (or in other words, rounded to zero.) For example, for any Calendar value x,
"P1M" (1 month) * "12" = "P12M" (12 months) "PT1M" (1 min) * "0.3" = "PT18S" (18 seconds) "P1M" (1 month) * "1.5" = IllegalStateException
new Duration("PT10.00099S").getTimeInMills(x) == 10000. new Duration("-PT10.00099S").getTimeInMills(x) == -10000.
Since the Duration class is immutable, this method doesn't change the value of this object. It simply computes a new Duration object and returns it.
The operation will be performed field by field with the precision of
BigDecimal
Note that this method uses the
addTo(Calendar)
. Since all the fields except seconds are restricted to hold integers, any fraction produced by the computation will be carried down toward the next lower unit. For example, if you multiply "P1D" (1 day) with "0.5", then it will be 0.5 day, which will be carried down to "PT12H" (12 hours). When fractions of month cannot be meaningfully carried down to days, or year to months, this will cause an
IllegalStateException
method, which may work incorectly with
Duration
to be thrown. For example if you multiple one month by 0.5.
To avoid
IllegalStateException
objects with very large values in its fields. See the
addTo(Calendar)
, use the
normalizeWith(Calendar)
method to remove the years and months fields.
method for details.
factor - to multiply by
returns a non-null valid Duration object
IllegalStateException
- if operation produces fraction in the months field.
the factor
negate
public abstract
Duration
public final longnegate
getTimeInMillis()
(DatestartInstant)
Returns a new Duration object whose value is -this.
Since the Duration class is immutable, this method doesn't change the value of this object. It simply computes a new Duration object and returns it.
Returns the length of the duration in milli-seconds.
If the seconds field carries more digits than milli-second order, those will be simply discarded (or in other words, rounded to zero.) For example, for any Date value x,
new Duration("PT10.00099S").getTimeInMills(x) == 10000. new Duration("-PT10.00099S").getTimeInMills(x) == -10000.
Note that this method uses the
addTo(Date)
method, which may work incorectly with
Duration
objects with very large values in its fields. See the
addTo(Date)
method for details.
always return a non-null valid Duration object.
publicabstract Duration normalizeWith(Calendar startTimeInstant)
Converts the years and months fields into the days field by using a specific time instant as the reference point.
For example, duration of one month normalizes to 31 days given the start time instance "July 8th 2003, 17:40:32".
Formally, the computation is done as follows:
the
cloned
the
the
the
two Calendars
in
milliseconds and converted to days, if a remainder occurs due to Daylight Savings Time, it is discarded
the
Note that since the Calendar class uses int to hold the value of year and month, this method may produce an unexpected result if this duration object holds a very large value in the years or months fields.
compare
public abstract int
publicDurationcompare
multiply(
Duration
duration)
(int factor)
Partial order relation comparison with this Duration instance.
Computes a new duration whose value is factor times longer than the value of this duration.
Comparison result must be in accordance with
W3C XML Schema 1.0 Part 2, Section 3.2.7.6.2,
Order relation on duration
.
This method is provided for the convenience. It is functionally equivalent to the following code:
multiply(new BigDecimal(String.valueOf(factor)))
DatatypeConstants.LESSER
DatatypeConstants.EQUAL
DatatypeConstants.GREATER
DatatypeConstants.INDETERMINATE
duration - to compare
the relationship between this Durationand duration parameter as
DatatypeConstants.LESSER
,
DatatypeConstants.EQUAL
,
DatatypeConstants.GREATER
or
DatatypeConstants.INDETERMINATE
.
Throws:
NullPointerException
- if duration is null.
isShorterThan(Duration)
,
isLongerThan(Duration)
isLongerThan
public boolean
public finalDurationisLongerThan
multiply(Duration
BigDecimalduration)
factor)
Checks if this duration object is strictly longer than another Duration object.
"P1M" (1 month) * "12" = "P12M" (12 months) "PT1M" (1 min) * "0.3" = "PT18S" (18 seconds) "P1M" (1 month) * "1.5" = IllegalStateException
Duration X is "longer" than Y if and only if X>Y as defined in the section 3.2.6.2 of the XML Schema 1.0 specification.
Since the
Duration
class is immutable, this method doesn't change the value of this object. It simply computes a new Duration object and returns it.
The operation will be performed field by field with the precision of
BigDecimal
. Since all the fields except seconds are restricted to hold integers, any fraction produced by the computation will be carried down toward the next lower unit. For example, if you multiply "P1D" (1 day) with "0.5", then it will be 0.5 day, which will be carried down to "PT12H" (12 hours). When fractions of month cannot be meaningfully carried down to days, or year to months, this will cause an
IllegalStateException
to be thrown. For example if you multiple one month by 0.5.
For example, "P1D" (one day) > "PT12H" (12 hours) and "P2Y" (two years) > "P23M" (23 months).
duration - Duration to test this Duration against.
true if the duration represented by this object is longer than the given duration. false otherwise.
NullPointerException
- if duration is null.
See Also:
isShorterThan(Duration)
,
compare(Duration duration)
isShorterThan
public boolean
public finalDurationisShorterThan
add(Durationduration)
rhs)
Checks if this duration object is strictly shorter than another Duration object.
Computes a new duration whose value is this+rhs.
"1 day" + "-3 days" = "-2 days" "1 year" + "1 day" = "1 year and 1 day" "-(1 hour,50 minutes)" + "-20 minutes" = "-(1 hours,70 minutes)" "15 hours" + "-3 days" = "-(2 days,9 hours)" "1 year" + "-1 day" = IllegalStateException
Since there's no way to meaningfully subtract 1 day from 1 month, there are cases where the operation fails in
IllegalStateException
.
Formally, the computation is defined as follows.
Firstly, we can assume that two
Duration
s to be added are both positive without losing generality (i.e., (-X)+Y=Y-X, X+(-Y)=X-Y, (-X)+(-Y)=-(X+Y))
Addition of two positive
Duration
s are simply defined as field by field addition where missing fields are treated as 0.
A field of the resulting
Duration
will be unset if and only if respective fields of two input
Duration
s are unset.
Note that lhs.add(rhs) will be always successful if lhs.signum()*rhs.signum()!=-1 or both of them are normalized.
duration
test
against.
true if duration parameter is shorter than this Duration, else false.
- if duration is null.
isLongerThan(Duration duration)
,
compare(Duration duration)
equals
public boolean
public finalDurationequals
subtract(Object
Durationduration)
rhs)
Checks if this duration object has the same duration as another Duration object.
Computes a new duration whose value is this-rhs.
For example, "P1D" (1 day) is equal to "PT24H" (24 hours).
For example:
"1 day" - "-3 days" = "4 days" "1 year" - "1 day" = IllegalStateException "-(1 hour,50 minutes)" - "-20 minutes" = "-(1hours,30 minutes)" "15 hours" - "-3 days" = "3 days and 15 hours" "1 year" - "-1 day" = "1 year and 1 day"
Duration X is equal to Y if and only if time instant t+X and t+Y are the same for all the test time instants specified in the section 3.2.6.2 of the XML Schema 1.0 specification.
Since there's no way to meaningfully subtract 1 day from 1 month, there are cases where the operation fails in
IllegalStateException
.
Note that there are cases where two Durations are "incomparable" to each other, like one month and 30 days. For example,
Formally the computation is defined as follows. First, we can assume that two
Duration
s are both positive without losing generality. (i.e., (-X)-Y=-(X+Y), X-(-Y)=X+Y, (-X)-(-Y)=-(X-Y))
!new Duration("P1M").isShorterThan(new Duration("P30D")) !new Duration("P1M").isLongerThan(new Duration("P30D")) !new Duration("P1M").equals(new Duration("P30D"))
Then two durations are subtracted field by field. If the sign of any non-zero field
F
is different from the sign of the most significant field, 1 (if
F
is negative) or -1 (otherwise) will be borrowed from the next bigger unit of
F
.
This process is repeated until all the non-zero fields have the same sign.
If a borrow occurs in the days field (in other words, if the computation needs to borrow 1 or -1 month to compensate days), then the computation fails by throwing an
IllegalStateException
.
Overrides:
equals
in class
Object
duration - A non-null valid Duration object.
true if this duration is the same length as duration. false if duration is not a Duration object or its length is different from this duration.
if
compare(Duration duration)
hashCode
public abstract int
publicDurationhashCode
negate()
Returns a hash code consistent with the definition of the equals method.
Since the
Duration
class is immutable, this method doesn't change the value of this object. It simply computes a new Duration object and returns it.
Overrides:
hashCode
in class
Object
public intsignum()
a hash code value for this object.
See Also:
Object.hashCode()
toString
public abstract
String
public voidtoString
addTo()
(Calendarcalendar)
Returns a string representation of this duration object.
Calls
Calendar.add(int,int)
in the order of YEARS, MONTHS, DAYS, HOURS, MINUTES, SECONDS, and MILLISECONDS if those fields are present. Because the
Calendar
class uses int to hold values, there are cases where this method won't work correctly (for example if values of fields exceed the range of int.)
The result is formatted according to the XML Schema 1.0 spec and can be always parsed back later into the equivalent duration object by
DatatypeFactory.newDuration(String lexicalRepresentation)
Also, since this duration class is a Gregorian duration, this method will not work correctly if the given
Calendar
.
object is based on some other calendar systems.
Formally, the following holds for any Duration object x:
Any fractional parts of this
Duration
object beyond milliseconds will be simply ignored. For example, if this duration is "P1.23456S", then 1 is added to SECONDS, 234 is added to MILLISECONDS, and the rest will be unused.
new Duration(x.toString()).equals(x)
Note that because
Calendar.add(int, int)
is using
int
,
Duration
with values beyond the range of
int
in its fields will cause overflow/underflow to the given
Calendar
.
XMLGregorianCalendar.add(Duration)
provides the same basic operation as this method while avoiding the overflow/underflow issues.
Overrides:
toString
in class
Object
Returns:
A non-null valid String representation of this Duration.
public voidaddTo(Datedate)
The given date is first converted into a
GregorianCalendar
, then the duration is added exactly like the
addTo(Calendar)
method.
The updated time instant is then converted back into a
Date
object and used to update the given
Date
object.
This somewhat redundant computation is necessary to unambiguously determine the duration of months and years.