Class PeriodicSchedule

  • All Implemented Interfaces:
    Serializable, org.joda.beans.Bean, org.joda.beans.ImmutableBean

    public final class PeriodicSchedule
    extends Object
    implements org.joda.beans.ImmutableBean, Serializable
    Definition of a periodic schedule.

    A periodic schedule is determined using a "periodic frequency". This splits the schedule into "regular" periods of a fixed length, such as every 3 months. Any remaining days are allocated to irregular "stubs" at the start and/or end.

    For example, a 24 month (2 year) swap might be divided into 3 month periods. The 24 month period is the overall schedule and the 3 month period is the periodic frequency.

    Note that a 23 month swap cannot be split into even 3 month periods. Instead, there will be a 2 month "initial" stub at the start, a 2 month "final" stub at the end or both an initial and final stub with a combined length of 2 months.

    Example

    This example creates a schedule for a 13 month swap cannot be split into 3 month periods with a long initial stub rolling at end-of-month:

      // example swap using builder
      BusinessDayAdjustment businessDayAdj =
        BusinessDayAdjustment.of(BusinessDayConventions.MODIFIED_FOLLOWING, GlobalHolidayCalendars.EUTA);
      PeriodicSchedule definition = PeriodicSchedule.builder()
          .startDate(LocalDate.of(2014, 2, 12))
          .endDate(LocalDate.of(2015, 3, 31))
          .businessDayAdjustment(businessDayAdj)
          .frequency(Frequency.P3M)
          .stubConvention(StubConvention.LONG_INITIAL)
          .rollConvention(RollConventions.EOM)
          .build();
      Schedule schedule = definition.createSchedule();
     
      // result
      period 1: 2014-02-12 to 2014-06-30
      period 2: 2014-06-30 to 2014-09-30
      period 3: 2014-09-30 to 2014-12-31
      period 4: 2014-12-31 to 2015-03-31
     

    Details about stubs and date rolling

    The stubs are specified using a combination of the StubConvention, RollConvention and dates.

    The explicit stub dates are checked first. An explicit stub occurs if 'firstRegularStartDate' or 'lastRegularEndDate' is present and they differ from 'startDate' and 'endDate'.

    If explicit stub dates are specified then they are used to lock the initial or final stub. If the stub convention is present, it is matched and validated against the locked stub. For example, if an initial stub is specified by dates and the stub convention is 'ShortInitial', 'LongInitial' or 'SmartInitial' then the convention is considered to be matched, thus the periodic frequency is applied using the implicit stub convention 'None'. If the stub convention does not match the dates, then an exception will be thrown during schedule creation. If the stub convention is not present, then the periodic frequency is applied using the implicit stub convention 'None'.

    If explicit stub dates are not specified then the stub convention is used. The convention selects whether to use the start date or the end date as the beginning of the schedule calculation. The beginning of the calculation must match the roll convention, unless the convention is 'EOM', in which case 'EOM' is only applied if the calculation starts at the end of the month.

    In all cases, the roll convention is used to fine-tune the dates. If not present or 'None', the convention is effectively implied from the first date of the calculation. All calculated dates will match the roll convention. If this is not possible due to the dates specified then an exception will be thrown during schedule creation.

    It is permitted to have 'firstRegularStartDate' equal to 'endDate', or 'lastRegularEndDate' equal to 'startDate'. In both cases, the effect is to define a schedule that is entirely "stub" and has no regular periods. The resulting schedule will retain the frequency specified here, even though it is not used.

    The schedule operates primarily on "unadjusted" dates. An unadjusted date can be any day, including non-business days. When the unadjusted schedule has been determined, the appropriate business day adjustment is applied to create a parallel schedule of "adjusted" dates.

    See Also:
    Serialized Form
    • Method Detail

      • of

        public static PeriodicSchedule of​(LocalDate unadjustedStartDate,
                                          LocalDate unadjustedEndDate,
                                          Frequency frequency,
                                          BusinessDayAdjustment businessDayAdjustment,
                                          StubConvention stubConvention,
                                          boolean preferEndOfMonth)
        Obtains an instance based on a stub convention and end-of-month flag.

        The business day adjustment is used for all dates. The stub convention is used to determine whether there are any stubs. If the end-of-month flag is true, then in any case of ambiguity the end-of-month will be chosen.

        Parameters:
        unadjustedStartDate - start date, which is the start of the first schedule period
        unadjustedEndDate - the end date, which is the end of the last schedule period
        frequency - the regular periodic frequency
        businessDayAdjustment - the business day adjustment to apply
        stubConvention - the non-null convention defining how to handle stubs
        preferEndOfMonth - whether to prefer the end-of-month when rolling
        Returns:
        the definition
      • of

        public static PeriodicSchedule of​(LocalDate unadjustedStartDate,
                                          LocalDate unadjustedEndDate,
                                          Frequency frequency,
                                          BusinessDayAdjustment businessDayAdjustment,
                                          StubConvention stubConvention,
                                          RollConvention rollConvention)
        Obtains an instance based on roll and stub conventions.

        The business day adjustment is used for all dates. The stub convention is used to determine whether there are any stubs. The roll convention is used to fine tune each rolled date.

        Parameters:
        unadjustedStartDate - start date, which is the start of the first schedule period
        unadjustedEndDate - the end date, which is the end of the last schedule period
        frequency - the regular periodic frequency
        businessDayAdjustment - the business day adjustment to apply
        stubConvention - the non-null convention defining how to handle stubs
        rollConvention - the non-null convention defining how to roll dates
        Returns:
        the definition
      • createSchedule

        public Schedule createSchedule​(ReferenceData refData,
                                       boolean combinePeriodsIfNecessary)
        Creates the schedule from the definition.

        The schedule consists of an optional initial stub, a number of regular periods and an optional final stub.

        The roll convention, stub convention and additional dates are all used to determine the schedule. If the roll convention is not present it will be defaulted from the stub convention, with 'None' as the default. If there are explicit stub dates then they will be used. If the stub convention is present, then it will be validated against the stub dates. If the stub convention and stub dates are not present, then no stubs are allowed.

        There is special handling for pre-adjusted start dates to avoid creating incorrect stubs. If all the following conditions hold true, then the unadjusted start date is treated as being the day-of-month implied by the roll convention (the adjusted date is unaffected).

        • the startDateBusinessDayAdjustment property equals BusinessDayAdjustment.NONE or the roll convention is 'EOM'
        • the roll convention is numeric or 'EOM'
        • applying businessDayAdjustment to the day-of-month implied by the roll convention yields the specified start date

        There is additional special handling for pre-adjusted first/last regular dates and the end date. If the following conditions hold true, then the unadjusted date is treated as being the day-of-month implied by the roll convention (the adjusted date is unaffected).

        • the roll convention is numeric or 'EOM'
        • applying businessDayAdjustment to the day-of-month implied by the roll convention yields the first/last regular date that was specified
        Parameters:
        refData - the reference data, used to find the holiday calendars
        combinePeriodsIfNecessary - determines whether periods should be combined if necessary
        Returns:
        the schedule
        Throws:
        ScheduleException - if the definition is invalid
      • createUnadjustedDates

        public ImmutableList<LocalDate> createUnadjustedDates()
        Creates the list of unadjusted dates in the schedule.

        The unadjusted date list will contain at least two elements, the start date and end date. Between those dates will be the calculated periodic schedule.

        The roll convention, stub convention and additional dates are all used to determine the schedule. If the roll convention is not present it will be defaulted from the stub convention, with 'None' as the default. If there are explicit stub dates then they will be used. If the stub convention is present, then it will be validated against the stub dates. If the stub convention and stub dates are not present, then no stubs are allowed. If the frequency is 'Term' explicit stub dates are disallowed, and the roll and stub convention are ignored.

        The special handling for last business day of month seen in createUnadjustedDates(ReferenceData) is not applied.

        Returns:
        the schedule of unadjusted dates
        Throws:
        ScheduleException - if the definition is invalid
      • createUnadjustedDates

        public ImmutableList<LocalDate> createUnadjustedDates​(ReferenceData refData)
        Creates the list of unadjusted dates in the schedule.

        The unadjusted date list will contain at least two elements, the start date and end date. Between those dates will be the calculated periodic schedule.

        The roll convention, stub convention and additional dates are all used to determine the schedule. If the roll convention is not present it will be defaulted from the stub convention, with 'None' as the default. If there are explicit stub dates then they will be used. If the stub convention is present, then it will be validated against the stub dates. If the stub convention and stub dates are not present, then no stubs are allowed. If the frequency is 'Term' explicit stub dates are disallowed, and the roll and stub convention are ignored.

        There is special handling for pre-adjusted start dates to avoid creating incorrect stubs. If all the following conditions hold true, then the unadjusted start date is treated as being the day-of-month implied by the roll convention (the adjusted date is unaffected).

        • the startDateBusinessDayAdjustment property equals BusinessDayAdjustment.NONE or the roll convention is 'EOM'
        • the roll convention is numeric or 'EOM'
        • applying businessDayAdjustment to the day-of-month implied by the roll convention yields the specified start date

        There is additional special handling for pre-adjusted first/last regular dates and the end date. If the following conditions hold true, then the unadjusted date is treated as being the day-of-month implied by the roll convention (the adjusted date is unaffected).

        • the roll convention is numeric or 'EOM'
        • applying businessDayAdjustment to the day-of-month implied by the roll convention yields the first/last regular date that was specified
        Parameters:
        refData - the reference data, used to find the holiday calendars
        Returns:
        the schedule of unadjusted dates
        Throws:
        ScheduleException - if the definition is invalid
      • createAdjustedDates

        public ImmutableList<LocalDate> createAdjustedDates​(ReferenceData refData)
        Creates the list of adjusted dates in the schedule.

        The adjusted date list will contain at least two elements, the start date and end date. Between those dates will be the calculated periodic schedule. Each date will be a valid business day as per the appropriate business day adjustment.

        The roll convention, stub convention and additional dates are all used to determine the schedule. If the roll convention is not present it will be defaulted from the stub convention, with 'None' as the default. If there are explicit stub dates then they will be used. If the stub convention is present, then it will be validated against the stub dates. If the stub convention and stub dates are not present, then no stubs are allowed.

        There is special handling for pre-adjusted start dates to avoid creating incorrect stubs. If all the following conditions hold true, then the unadjusted start date is treated as being the day-of-month implied by the roll convention (the adjusted date is unaffected).

        • the startDateBusinessDayAdjustment property equals BusinessDayAdjustment.NONE or the roll convention is 'EOM'
        • the roll convention is numeric or 'EOM'
        • applying businessDayAdjustment to the day-of-month implied by the roll convention yields the specified start date

        There is additional special handling for pre-adjusted first/last regular dates and the end date. If the following conditions hold true, then the unadjusted date is treated as being the day-of-month implied by the roll convention (the adjusted date is unaffected).

        • the roll convention is numeric or 'EOM'
        • applying businessDayAdjustment to the day-of-month implied by the roll convention yields the first/last regular date that was specified
        Parameters:
        refData - the reference data, used to find the holiday calendar
        Returns:
        the schedule of dates adjusted to valid business days
        Throws:
        ScheduleException - if the definition is invalid
      • calculatedRollConvention

        public RollConvention calculatedRollConvention()
        Gets the applicable roll convention defining how to roll dates.

        The schedule periods are determined at the high level by repeatedly adding the frequency to the start date, or subtracting it from the end date. The roll convention provides the detailed rule to adjust the day-of-month or day-of-week.

        The applicable roll convention is a non-null value. If the roll convention property is not present, this is determined from the stub convention, dates and frequency, defaulting to 'None' if necessary.

        Returns:
        the non-null roll convention
      • calculatedFirstRegularStartDate

        public LocalDate calculatedFirstRegularStartDate()
        Calculates the applicable first regular start date.

        This will be either 'firstRegularStartDate' or 'startDate'.

        Returns:
        the non-null start date of the first regular period
      • calculatedLastRegularEndDate

        public LocalDate calculatedLastRegularEndDate()
        Calculates the applicable last regular end date.

        This will be either 'lastRegularEndDate' or 'endDate'.

        Returns:
        the non-null end date of the last regular period
      • calculatedStartDate

        public AdjustableDate calculatedStartDate()
        Calculates the applicable start date.

        The result combines the start date and the appropriate business day adjustment. If the override start date is present, it will be returned.

        Returns:
        the calculated start date
      • calculatedEndDate

        public AdjustableDate calculatedEndDate()
        Calculates the applicable end date.

        The result combines the end date and the appropriate business day adjustment.

        Returns:
        the calculated end date
      • replaceStartDate

        public PeriodicSchedule replaceStartDate​(LocalDate adjustedStartDate)
        Returns an instance based on this schedule with the start date replaced.

        This returns a new instance with the schedule altered to have the specified start date. The specified date is considered to be adjusted, thus startDateBusinessDayAdjustment is set to 'None'. The firstRegularStartDate and overrideStartDate fields are also removed.

        The stub convention is typically altered to be 'SmartInitial'. The algorithm retains the 'ShortInitial' and 'LongInitial' conventions as is. The algorithm examines "Final" conventions to try and set the lastRegularEndDate via schedule generation allowing the stub convention to become 'SmartInitial'.

        Parameters:
        adjustedStartDate - the proposed start date, which is considered to be adjusted
        Returns:
        a schedule with the proposed start date
        Throws:
        IllegalArgumentException - if the schedule start date cannot be replaced with the proposed start date
      • meta

        public static PeriodicSchedule.Meta meta()
        The meta-bean for PeriodicSchedule.
        Returns:
        the meta-bean, not null
      • builder

        public static PeriodicSchedule.Builder builder()
        Returns a builder used to create an instance of the bean.
        Returns:
        the builder, not null
      • metaBean

        public PeriodicSchedule.Meta metaBean()
        Specified by:
        metaBean in interface org.joda.beans.Bean
      • getStartDate

        public LocalDate getStartDate()
        Gets the start date, which is the start of the first schedule period.

        This is the start date of the schedule, it is unadjusted and as such might be a weekend or holiday. Any applicable business day adjustment will be applied when creating the schedule. This is also known as the unadjusted effective date.

        In most cases, the start date of a financial instrument is just after the trade date, such as two business days later. However, the start date of a schedule is permitted to be any date, which includes dates before or after the trade date.

        Returns:
        the value of the property, not null
      • getEndDate

        public LocalDate getEndDate()
        Gets the end date, which is the end of the last schedule period.

        This is the end date of the schedule, it is unadjusted and as such might be a weekend or holiday. Any applicable business day adjustment will be applied when creating the schedule. This is also known as the unadjusted maturity date or unadjusted termination date. This date must be after the start date.

        Returns:
        the value of the property, not null
      • getFrequency

        public Frequency getFrequency()
        Gets the regular periodic frequency to use.

        Most dates are calculated using a regular periodic frequency, such as every 3 months. The actual day-of-month or day-of-week is selected using the roll and stub conventions.

        Returns:
        the value of the property, not null
      • getBusinessDayAdjustment

        public BusinessDayAdjustment getBusinessDayAdjustment()
        Gets the business day adjustment to apply.

        Each date in the calculated schedule is determined without taking into account weekends and holidays. The adjustment specified here is used to convert those dates to valid business days.

        The start date and end date may have their own business day adjustment rules. If those are not present, then this adjustment is used instead.

        Returns:
        the value of the property, not null
      • getStartDateBusinessDayAdjustment

        public Optional<BusinessDayAdjustment> getStartDateBusinessDayAdjustment()
        Gets the optional business day adjustment to apply to the start date.

        The start date property is an unadjusted date and as such might be a weekend or holiday. The adjustment specified here is used to convert the start date to a valid business day.

        If this property is not present, the standard businessDayAdjustment property is used instead.

        Returns:
        the optional value of the property, not null
      • getEndDateBusinessDayAdjustment

        public Optional<BusinessDayAdjustment> getEndDateBusinessDayAdjustment()
        Gets the optional business day adjustment to apply to the end date.

        The end date property is an unadjusted date and as such might be a weekend or holiday. The adjustment specified here is used to convert the end date to a valid business day.

        If this property is not present, the standard businessDayAdjustment property is used instead.

        Returns:
        the optional value of the property, not null
      • getStubConvention

        public Optional<StubConvention> getStubConvention()
        Gets the optional convention defining how to handle stubs.

        The stub convention is used during schedule construction to determine whether the irregular remaining period occurs at the start or end of the schedule. It also determines whether the irregular period is shorter or longer than the regular period. This property interacts with the "explicit dates" of getFirstRegularStartDate() and getLastRegularEndDate().

        The convention 'None' may be used to explicitly indicate there are no stubs. There must be no explicit dates. This will be validated during schedule construction.

        The convention 'Both' may be used to explicitly indicate there is both an initial and final stub. The stubs themselves must be specified using explicit dates. This will be validated during schedule construction.

        The conventions 'ShortInitial', 'LongInitial', 'SmartInitial', 'ShortFinal', 'LongFinal' and 'SmartFinal' are used to indicate the type of stub to be generated. The exact behavior varies depending on whether there are explicit dates or not:

        If explicit dates are specified, then the combination of stub convention an explicit date will be validated during schedule construction. For example, the combination of an explicit dated initial stub and a stub convention of 'ShortInitial', 'LongInitial' or 'SmartInitial' is valid, but other stub conventions, such as 'ShortFinal' or 'None' would be invalid.

        If explicit dates are not specified, then it is not required that a stub is generated. The convention determines whether to generate dates from the start date forward, or the end date backwards. Date generation may or may not result in a stub, but if it does then the stub will be of the correct type.

        When the stub convention is not present, the generation of stubs is based on the presence or absence of the explicit dates. When there are no explicit stubs and there is a roll convention that matches the start or end date, then the stub convention will be defaulted to 'SmartInitial' or 'SmartFinal'.

        Returns:
        the optional value of the property, not null
      • getRollConvention

        public Optional<RollConvention> getRollConvention()
        Gets the optional convention defining how to roll dates.

        The schedule periods are determined at the high level by repeatedly adding the frequency to the start date, or subtracting it from the end date. The roll convention provides the detailed rule to adjust the day-of-month or day-of-week.

        During schedule generation, if this is present it will be used to determine the schedule. If not present, then the roll convention will be implied.

        Returns:
        the optional value of the property, not null
      • getFirstRegularStartDate

        public Optional<LocalDate> getFirstRegularStartDate()
        Gets the optional start date of the first regular schedule period, which is the end date of the initial stub.

        This is used to identify the boundary date between the initial stub and the first regular schedule period.

        This is an unadjusted date, and as such it might not be a valid business day. This date must be on or after 'startDate' and on or before 'endDate'.

        During schedule generation, if this is present it will be used to determine the schedule. If not present, then the overall schedule start date will be used instead, resulting in no initial stub.

        Returns:
        the optional value of the property, not null
      • getLastRegularEndDate

        public Optional<LocalDate> getLastRegularEndDate()
        Gets the optional end date of the last regular schedule period, which is the start date of the final stub.

        This is used to identify the boundary date between the last regular schedule period and the final stub.

        This is an unadjusted date, and as such it might not be a valid business day. This date must be one or after 'startDate', on or after 'firstRegularStartDate' and on or before 'endDate'.

        During schedule generation, if this is present it will be used to determine the schedule. If not present, then the overall schedule end date will be used instead, resulting in no final stub.

        Returns:
        the optional value of the property, not null
      • getOverrideStartDate

        public Optional<AdjustableDate> getOverrideStartDate()
        Gets the optional start date of the first schedule period, overriding normal schedule generation.

        This property is rarely used, and is generally needed when accrual starts before the effective date. If specified, it overrides the start date of the first period once schedule generation has been completed. Note that all schedule generation rules apply to 'startDate', with this applied as a final step. This field primarily exists to support the FpML 'firstPeriodStartDate' concept.

        If a roll convention is explicitly specified and the regular start date does not match it, then the override will be used when generating regular periods.

        If set, it should be different to the start date, although this is not validated. Validation does check that it is on or before 'firstRegularStartDate' and 'lastRegularEndDate', and before 'endDate'.

        During schedule generation, if this is present it will be used to override the start date of the first generated schedule period. If not present, then the start of the first period will be the normal start date.

        Returns:
        the optional value of the property, not null
      • toBuilder

        public PeriodicSchedule.Builder toBuilder()
        Returns a builder that allows this bean to be mutated.
        Returns:
        the mutable builder, not null
      • hashCode

        public int hashCode()
        Overrides:
        hashCode in class Object