Welcome back.

This post is the third in a series covering chapter 4 of my book; the first post is here. This week, a few examples of interest-rate coupons.

Registration for my Introduction to QuantLib Development course is still open; it’s three days of presentations and exercises about the architecture of QuantLib, and it’s going to be in London from 24 to 26 March. I look forward to see you there.

Follow me on Twitter if you want to be notified of new posts, or add me to your circles, or subscribe via RSS: the buttons for that are in the footer. Also, make sure to check my Training page.

Example: LIBOR coupons

The most common kind of floating-rate coupon is the one paying the rate fixed by a LIBOR index. A minimal implementation of such a coupon is shown in listing 4.6.

Listing 4.6: Minimal implementation of the IborCoupon class.

    class IborCoupon : public FloatingRateCoupon {
      public:
        IborCoupon(const Date& paymentDate,
                   const Real nominal,
                   const Date& startDate,
                   const Date& endDate,
                   const Natural fixingDays,
                   const boost::shared_ptr<IborIndex>& index,
                   const Real gearing = 1.0,
                   const Spread spread = 0.0,
                   const Date& refPeriodStart = Date(),
                   const Date& refPeriodEnd = Date(),
                   const DayCounter& dayCounter = DayCounter(),
                   bool isInArrears = false)
        : FloatingRateCoupon(paymentDate, nominal,
                             startDate, endDate,
                             fixingDays, index, gearing, spread,
                             refPeriodStart, refPeriodEnd,
                             dayCounter, inArrears) {}
    };

The only required member is the constructor. It takes the same arguments as FloatingRateCoupon, but specializes the type of the passed index; it constrains this argument to be a pointer to an instance of the IborIndex class, rather than the more generic InterestRateIndex (the Ibor name was generalized from the common suffix of EURIBOR, LIBOR, and a number of like indexes). All arguments are simply forwarded to the constructor of the parent class; index needs no particular treatment, since shared pointers to a derived class can be implicitly upcast to pointers to its base class.

Of course, the real pricing work wil be done by pricers. Listing 4.7 shows a partial implementation of one of them, namely, the BlackIborCouponPricer class; the Black part of the name refers to the Black model used for calculating the adjustment (if any) and possible caps or floors on the index fixing.

Listing 4.7: Partial implementation of the BlackIborCouponPricer class.

    class BlackIborCouponPricer : public FloatingRateCouponPricer {
      public:
        BlackIborCouponPricer(
            const Handle<OptionletVolatilityStructure>& v =
                           Handle<OptionletVolatilityStructure>())
        : capletVol_(v) {
            registerWith(capletVol_);
        }
        void initialize(const FloatingRateCoupon& coupon) {
            coupon_ = dynamic_cast<const IborCoupon*>(&coupon);
            gearing_ = coupon_->gearing();
            spread_ = coupon_->spread();
        }
        Rate swapletRate() const {
            return gearing_ * (adjustedFixing() + spread_);
        }
        // other methods, not shown
      protected:
        virtual Rate adjustedFixing(
                              Rate fixing = Null<Rate>()) const {

            if (fixing == Null<Rate>())
                fixing = coupon_->indexFixing();

            Real adjustement = 0.0;
            if (!coupon_->isInArrears()) {
                adjustement = 0.0;
            } else {
                QL_REQUIRE(!capletVolatility().empty(),
                           "missing optionlet volatility");
                adjustment = // formula implementation, not shown
            }

            return fixing + adjustement;
        }
        const IborCoupon* coupon_;
        Real gearing_;
        Spread spread_;
        Handle<OptionletVolatilityStructure> capletVol_;
    };

The constructor takes a handle to a term structure that describes the volatility of the LIBOR rate, stores it, and registers with it as an observer. If the coupon rate is not fixed in arrears, and if no cap or floor is defined, the volatility is not used; in that case, the handle can be empty (or can be omitted from the constructor call).

The initialize method checks that the passed coupon has the correct type by downcasting it to IborCoupon. If the cast succeeds, a few results can then be precomputed. Here—more for illustration than for anything else—we store the coupon gearing and spread in two data members; this will allow to write the remaining code more concisely. The swapletRate method simply applies the stored gearing and spread to the adjusted rate, whose calculation is delegated to the adjustedFixing method. If the coupon fixes at the beginning of its tenor, the adjusted rate is just the fixing of the underlying index. If the coupon fixes in arrears, a convexity adjustment is calculated and added to the fixing; I don’t show the formula implementation here, but only the check for a valid caplet volatility. Other methods such as capletRate are not shown here; you can read their implementation in the library.

This would be all (and would make for a clean but very short example) were it not for those meddling kids—namely, for the common practice of using par coupons to price floating-rate notes. The library should allow one to choose whether or not to follow this practice; and as usual, there’s at least a couple of ways to do it.

One possible way (shown in listing 4.8) is to bypass the pricer machinery and override the rate method for LIBOR coupons.

Listing 4.8: Extension of the IborCoupon class to support par coupons.

    class IborCoupon : public FloatingRateCoupon {
      public:
        // constructor as before

        Rate rate() const {

            #ifndef QL_USE_INDEXED_COUPON
            if (!isInArrears()) {
                Rate parRate = // calculation, not shown
                return gearing()*(parRate + spread());
            }
            #endif
            
            return FloatingRateCoupon::rate();
        }
    };

If par coupons are enabled by setting a compilation flag, and if the coupon is not in arrears (in which case we still need a pricer), a built-in par-rate calculation is used; otherwise, the method call is forwarded to the base-class method, which in turn delegates the calculation to the pricer. This works, but it has disadvantages. On the one hand, one can still set pricers to the coupon, but with no observable effect. On the other hand, different index fixings would be used for in-arrears and not in-arrears coupons fixing on the same date, which could throw off parity relationships or, worse, hedges.

A probably better way would be to implement a par-coupon pricer explicitly. As shown in listing 4.9, this can be done by inheriting from the Black pricer described earlier.

Listing 4.9: Sketch of the ParCouponPricer class.

    class ParCouponPricer : public BlackIborCouponPricer {
      public:
        // constructor, not shown

      protected:
        virtual Rate adjustedFixing(
                              Rate fixing = Null<Rate>()) const {

            if (fixing == Null<Rate>()) {
                Handle<YieldTermStructure> riskFreeCurve =
                    index->termStructure();
                fixing = // calculation of par rate, not shown
            }

            return BlackIborCouponPricer::adjustedFixing(fixing);
        }
    };

The derived pricer just needs to override the adjustedFixing method; instead of asking the stored index for its fixing, it would extract its risk-free curve and use it to calculate the par rate. This is somewhat cleaner than overriding rate in the coupon class, doesn’t suffer from the same disadvantages, and allows one to make the choice at run time.

This approach still has a problem, though; the convexityAdjustment method will return the difference between the par fixing and the index fixing, which is not due to convexity effects. (The same problem must be faced when overriding the coupon’s rate method.) Unfortunately, it is not clear how to fix this—or at least, it is not clear to me—although a few possibilities come to mind. One is to override convexityAdjustment to detect par coupons and return a null adjustment, but it wouldn’t work for in-arrears coupons. Another is to rename the method to adjustment and make it more generic, but this would lose information. The best one is probably to delegate the calculation of the convexity adjustment to the pricer; this might also help to overcome the fragility issues that I mentioned on the previous post when I described the adjustedFixing method.

The current way? It’s a bit of a bummer. Read the aside below.

Aside: breach of contract.

The current implementation of IborCoupon enables par coupons by overriding the indexFixing method and making it return the par rate. It works, in a way; the coupon methods return the correct amount, and even the expected null convexity adjustment (the latter doesn’t hold for other implementations and might be the reason of this choice).

However, the implementation is wrong, since it breaks the semantics of the method; it no longer returns the index fixing. A future release should change the code so that the whole class interface works as declared.

Example: capped/floored coupons

Caps and floors are features that can be applied to any kind of floating-rate coupon. In our framework, that means that we’ll want to add the features, possibly in a generic way, to a number of classes derived from FloatingRateCoupon.

This requirement suggests some flavor of the Decorator pattern. The implementation of the resulting CappedFlooredCoupon class is shown in listing 4.10.

Listing 4.10: Implementation of the CappedFlooredCoupon class.

    class CappedFlooredCoupon : public FloatingRateCoupon {
      public:
        CappedFlooredCoupon(
                  const shared_ptr<FloatingRateCoupon>& underlying,
                  Rate cap = Null<Rate>(),
                  Rate floor = Null<Rate>());
        Rate rate() const;
        Rate convexityAdjustment() const;

        bool isCapped() const { return isCapped_; }
        bool isFloored() const { return isFloored_; }
        Rate cap() const;
        Rate floor() const;
        Rate effectiveCap() const;
        Rate effectiveFloor() const;

        virtual void accept(AcyclicVisitor&);

        void setPricer(
                const shared_ptr<FloatingRateCouponPricer>& pricer);
    protected:
        shared_ptr<FloatingRateCoupon> underlying_;
        bool isCapped_, isFloored_;
        Rate cap_, floor_;
    };

As we will see shortly, the class follows the canonical form of the Decorator pattern, storing a pointer to the base FloatingRateCoupon class, adding behavior where required and calling the methods of the stored object otherwise. However, note that C++, unlike other languages, provides another way to implement the Decorator pattern: namely, we could have combined templates and inheritance to write something like

    template <class CouponType>
    class CappedFloored : public CouponType;

This class template would be used to instantiate a number of classes (such as, e.g., CappedFloored<IborCoupon> or CappedFloored<CmsCoupon>) that would add behavior where required and call the methods of their respective base classes otherwise. At this time, I don’t see any compelling reason for the template implementation to replace the existing one; but out of interest, during the description of CappedFlooredCoupon—which I’ll start without further ado—I’ll point out where the class template would have differed, for better or worse.

Not surprisingly, the constructor takes a FloatingRateCoupon instance to decorate and stores it in a data member.

    CappedFlooredCoupon::CappedFlooredCoupon(
            const boost::shared_ptr<FloatingRateCoupon>& underlying,
            Rate cap, Rate floor)
    : FloatingRateCoupon(underlying->date(),
                         underlying->nominal(),
                         ...other coupon parameters...),
      underlying_(underlying),
      isCapped_(false), isFloored_(false) {

        if (gearing_ > 0) {
            if (cap != Null<Rate>()) {
                isCapped_ = true;
                cap_ = cap;
            }
            if (floor != Null<Rate>()) {
                isFloored_ = true;
                floor_ = floor;
            }
        } else {
            if (cap != Null<Rate>()) {
                isFloored_ = true;
                floor_ = cap;
            }
            if (floor != Null<Rate>()) {
                isCapped_ = true;
                cap_ = floor;
            }
        }
        registerWith(underlying);
    }

What might come as a surprise is that the constructor also extracts data from the passed coupon and copies them into its own data members by passing them to the base FloatingRateCoupon constructor. This is a departure from the usual implementation of the pattern, which would forward all method calls to the stored underlying coupon using code such as

    Date CappedFlooredCoupon::startDate() const {
        return underlying_->startDate();
    }

Instead, this implementation holds coupon state of its own and uses it to provide non-decorated behavior; for instance, the startDate method will just return the copied data member. This causes some duplication of state, which is not optimal; but on the other hand, it avoids writing quite a few forwarding methods. The alternative would be to make all Coupon methods virtual and override them all.

The design might be a bit cleaner if we were to use template inheritance. In that case, the coupon to be decorated would be the decorator itself, and duplication of state would be avoided. However, the constructor would still need to copy state; we’d have to write it as

    template <class CouponType>
    CappedFlooredCoupon(const CouponType& underlying,
                        Rate cap, Rate floor)
    : CouponType(underlying), ...

and not in the more desirable way, i.e., as a constructor taking the arguments required to instantiate the underlying; we’d have to build it externally to pass it, copy it, and throw it away afterwards. This is on the one hand, because of the so-called forwarding problem [1]; and on the other hand, because coupons tend to take quite a few parameters, and we’d probably need to give CappedFlooredCoupon about a dozen template constructors to accept them all. Note that both problems are due to the fact that we’re still using C++03 to support older compiler; they would be solved in C++11 by perfect forwarding [2] and variadic templates [3], respectively, so we might revisit this design in the future.

The other constructor arguments are the cap and floor rates. If either of them is not needed, client code can pass Null<Rate>() to disable it. The passed rates are stored in two data members—with a couple of twists. The first is that, besides two data members for the cap and floor rates, the class also stores two booleans that tell whether they’re enabled or disabled. This is somewhat different from what is done in several other places in the library; usually, we just store the value and rely on comparison with Null<Rate>() to see whether it’s enabled. Storing a separate boolean member might seem redundant, but it avoids using the null value as a magic number. It would be better yet to use a type, such as boost::optional, that is designed to store a possibly null value and has cleaner semantics. In fact, I’d like to delete the Null class and replace it with optional everywhere, but it would break too much client code at this time.

The second twist is that a cap might not be stored as a cap. If the gearing of the underlying is positive, all is as expected. If it’s negative, the cap is stored in the floor_ data member and vice versa. This was probably based on the fact that, when the gearing is negative, a cap on the coupon rate is in fact a floor on the underlying index rate. However, it might be confusing and complicates both the constructor and the inspectors. I think it would be better to store the cap and floor as they are passed.

The rate method is where the behavior of the underlying coupon is decorated.

    Rate CappedFlooredCoupon::rate() const {
        Rate swapletRate = underlying_->rate();
        Rate floorletRate = isFloored_ ?
            underlying_->pricer()->floorletRate(effectiveFloor()) :
            0.0;
        Rate capletRate = isCapped_ ?
            underlying_->pricer()->capletRate(effectiveCap());
            0.0;
        return swapletRate + floorletRate - capletRate;
    }

In our case, this means modifying the coupon rate by adding a floorlet rate (i.e., the rate that, accrued over the life of the coupon, gives the price of the floorlet) and subtracting a caplet rate. The calculation of the two rates is delegated to the pricer used for the underlying coupon, which requires as arguments the effective cap and floor rates; as we’ll see shortly, these are the cap and floor rates that apply to the underlying index fixing rather than to the coupon rate.

The next method is convexityAdjustment.

    Rate CappedFlooredCoupon::convexityAdjustment() const {
        return underlying_->convexityAdjustment();
    }

It forwards to the corresponding method in the underlying coupon, and returns the result without changes (incidentally, we’d get this behavior for free—i.e., without having to override the method—if we were to use template inheritance). This might look a bit strange, since applying the cap or floor to the coupon can change the rate enough to make the adjustment moot; but taking the cap and floor rates into account would change the meaning of the method, which was defined to return the adjustment of the underlying index fixing.

The cap and floor inspectors return the passed cap and floor, possibly performing an inverse flip if a negative coupon gearing caused the constructor to flip the cap and floor data members.

    Rate CappedFlooredCoupon::cap() const {
        if ( (gearing_ > 0) && isCapped_)
                return cap_;
        if ( (gearing_ < 0) && isFloored_)
            return floor_;
        return Null<Rate>();
    }

    Rate CappedFlooredCoupon::floor() const {
        if ( (gearing_ > 0) && isFloored_)
            return floor_;
        if ( (gearing_ < 0) && isCapped_)
            return cap_;
        return Null<Rate>();
    }

As I said, this might be improved by storing cap and floor unmodified. If necessary, the flip would be performed inside the effectiveCap and effectiveFloor method, that currently (the flip being already performed) only adjust the cap and floor for the coupon gearing and spread, thus returning the cap and floor on the underlying index fixing.

    Rate CappedFlooredCoupon::effectiveCap() const {
        if (isCapped_)
            return (cap_ - spread())/gearing();
        else
            return Null<Rate>();
    }

    Rate CappedFlooredCoupon::effectiveFloor() const {
        if (isFloored_)
            return (floor_ - spread())/gearing();
        else
            return Null<Rate>();
    }

Finally, the setPricer method.

    void CappedFlooredCoupon::setPricer(
               const shared_ptr<FloatingRateCouponPricer>& pricer) {
        FloatingRateCoupon::setPricer(pricer);
        underlying_->setPricer(pricer);
    }

In order to keep everything consistent, the passed pricer is set to both the underlying coupon and to this instance. It smells a bit: it’s a bit of duplication of state, and a bit more work than would be necessary if we had written a pure Decorator—or if we had used template inheritance. But I’ve committed worse sins in my life as a developer; and such duplication as we have is confined in this single method.

At this point, the CappedFlooredCoupon class is complete. To wrap up the example, I’ll mention that it’s possible to inherit from it as a convenience for instantiating capped or floored coupons; one such derived class is shown in listing 4.11 and specializes the base class to build capped or floored LIBOR coupons.

Listing 4.11: Implementation of the CappedFlooredIborCoupon class.

    class CappedFlooredIborCoupon : public CappedFlooredCoupon {
      public:
        CappedFlooredIborCoupon(
                const Date& paymentDate,
                const Real nominal,
                const Date& startDate,
                const Date& endDate,
                ...other IBOR-coupon arguments...
                const Rate cap = Null<Rate>(),
                const Rate floor = Null<Rate>(),
                ...remaining arguments...)
        : CappedFlooredCoupon(
            shared_ptr<FloatingRateCoupon>(new IborCoupon(...)),
            cap, floor) {}
    };

The class only defines a constructor; instead of a built coupon instance, it takes the arguments needed to build the underling coupon, instantiates it, and passes it to the constructor of the base class. This way, it takes away a bit of the chore in creating a coupon. The implementation would be identical if CappedFlooredCoupon were a class template.

Finally, a word on a possible alternative implementation. The class I described in this example applies a cap and a floor, both possibly null; which forces the class to contain a couple of booleans and some logic to keep track of what is enabled or disabled. This might be avoided if the cap and the floor were two separate decorators; each one could be applied separately, without the need of storing a null for the other one. However, two separate decorators with similar semantics would probably cause some duplicated code; and one decorator with a flag to select whether it’s a cap or a floor would need some logic to manage the flag. If you want to get some exercise by giving this implementation a try, you’re welcome to contribute it to see how it compares to the current one.

Bibliography

[1] P. Dimov, H.E. Hinnant and D. Abrahams, The Forwarding Problem: Arguments. C++ Standards Committee Paper N1385, 2002.
[2] H.E. Hinnant, B. Stroustrup and B. Kozicki, A Brief Introduction to Rvalue References. C++ Standards Committee Paper N2027, 2006.
[3] D. Gregor, A Brief Introduction to Variadic Templates. C++ Standards Committee Paper N2087, 2006.