Coverage Report

Created: 2026-02-03 07:02

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/quantlib/ql/experimental/volatility/sviinterpolatedsmilesection.cpp
Line
Count
Source
1
/* -*- mode: c++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2
3
/*
4
 Copyright (C) 2014 Peter Caspers
5
6
 This file is part of QuantLib, a free-software/open-source library
7
 for financial quantitative analysts and developers - http://quantlib.org/
8
9
 QuantLib is free software: you can redistribute it and/or modify it
10
 under the terms of the QuantLib license.  You should have received a
11
 copy of the license along with this program; if not, please email
12
 <quantlib-dev@lists.sf.net>. The license is also available online at
13
 <https://www.quantlib.org/license.shtml>.
14
15
 This program is distributed in the hope that it will be useful, but WITHOUT
16
 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
17
 FOR A PARTICULAR PURPOSE.  See the license for more details.
18
*/
19
20
#include <ql/experimental/volatility/sviinterpolatedsmilesection.hpp>
21
#include <ql/quotes/simplequote.hpp>
22
#include <ql/settings.hpp>
23
#include <utility>
24
25
namespace QuantLib {
26
27
    SviInterpolatedSmileSection::SviInterpolatedSmileSection(
28
        const Date& optionDate,
29
        Handle<Quote> forward,
30
        const std::vector<Rate>& strikes,
31
        bool hasFloatingStrikes,
32
        Handle<Quote> atmVolatility,
33
        const std::vector<Handle<Quote> >& volHandles,
34
        Real a,
35
        Real b,
36
        Real sigma,
37
        Real rho,
38
        Real m,
39
        bool isAFixed,
40
        bool isBFixed,
41
        bool isSigmaFixed,
42
        bool isRhoFixed,
43
        bool isMFixed,
44
        bool vegaWeighted,
45
        ext::shared_ptr<EndCriteria> endCriteria,
46
        ext::shared_ptr<OptimizationMethod> method,
47
        const DayCounter& dc)
48
0
    : SmileSection(optionDate, dc), forward_(std::move(forward)),
49
0
      atmVolatility_(std::move(atmVolatility)), volHandles_(volHandles), strikes_(strikes),
50
0
      actualStrikes_(strikes), hasFloatingStrikes_(hasFloatingStrikes), vols_(volHandles.size()),
51
0
      a_(a), b_(b), sigma_(sigma), rho_(rho), m_(m), isAFixed_(isAFixed), isBFixed_(isBFixed),
52
0
      isSigmaFixed_(isSigmaFixed), isRhoFixed_(isRhoFixed), isMFixed_(isMFixed),
53
0
      vegaWeighted_(vegaWeighted), endCriteria_(std::move(endCriteria)),
54
0
      method_(std::move(method)) {
55
56
0
        LazyObject::registerWith(forward_);
57
0
        LazyObject::registerWith(atmVolatility_);
58
0
        for (auto& volHandle : volHandles_)
59
0
            LazyObject::registerWith(volHandle);
60
0
    }
Unexecuted instantiation: QuantLib::SviInterpolatedSmileSection::SviInterpolatedSmileSection(QuantLib::Date const&, QuantLib::Handle<QuantLib::Quote>, std::__1::vector<double, std::__1::allocator<double> > const&, bool, QuantLib::Handle<QuantLib::Quote>, std::__1::vector<QuantLib::Handle<QuantLib::Quote>, std::__1::allocator<QuantLib::Handle<QuantLib::Quote> > > const&, double, double, double, double, double, bool, bool, bool, bool, bool, bool, boost::shared_ptr<QuantLib::EndCriteria>, boost::shared_ptr<QuantLib::OptimizationMethod>, QuantLib::DayCounter const&)
Unexecuted instantiation: QuantLib::SviInterpolatedSmileSection::SviInterpolatedSmileSection(QuantLib::Date const&, QuantLib::Handle<QuantLib::Quote>, std::__1::vector<double, std::__1::allocator<double> > const&, bool, QuantLib::Handle<QuantLib::Quote>, std::__1::vector<QuantLib::Handle<QuantLib::Quote>, std::__1::allocator<QuantLib::Handle<QuantLib::Quote> > > const&, double, double, double, double, double, bool, bool, bool, bool, bool, bool, boost::shared_ptr<QuantLib::EndCriteria>, boost::shared_ptr<QuantLib::OptimizationMethod>, QuantLib::DayCounter const&)
61
62
    SviInterpolatedSmileSection::SviInterpolatedSmileSection(
63
        const Date& optionDate,
64
        const Rate& forward,
65
        const std::vector<Rate>& strikes,
66
        bool hasFloatingStrikes,
67
        const Volatility& atmVolatility,
68
        const std::vector<Volatility>& volHandles,
69
        Real a,
70
        Real b,
71
        Real sigma,
72
        Real rho,
73
        Real m,
74
        bool isAFixed,
75
        bool isBFixed,
76
        bool isSigmaFixed,
77
        bool isRhoFixed,
78
        bool isMFixed,
79
        bool vegaWeighted,
80
        ext::shared_ptr<EndCriteria> endCriteria,
81
        ext::shared_ptr<OptimizationMethod> method,
82
        const DayCounter& dc)
83
0
    : SmileSection(optionDate, dc),
84
0
      forward_(Handle<Quote>(ext::shared_ptr<Quote>(new SimpleQuote(forward)))),
85
0
      atmVolatility_(Handle<Quote>(ext::shared_ptr<Quote>(new SimpleQuote(atmVolatility)))),
86
0
      volHandles_(volHandles.size()), strikes_(strikes), actualStrikes_(strikes),
87
0
      hasFloatingStrikes_(hasFloatingStrikes), vols_(volHandles.size()), a_(a), b_(b),
88
0
      sigma_(sigma), rho_(rho), m_(m), isAFixed_(isAFixed), isBFixed_(isBFixed),
89
0
      isSigmaFixed_(isSigmaFixed), isRhoFixed_(isRhoFixed), isMFixed_(isMFixed),
90
0
      vegaWeighted_(vegaWeighted), endCriteria_(std::move(endCriteria)),
91
0
      method_(std::move(method)) {
92
93
0
        for (Size i = 0; i < volHandles_.size(); ++i)
94
0
            volHandles_[i] = Handle<Quote>(ext::shared_ptr<Quote>(new SimpleQuote(volHandles[i])));
95
0
    }
Unexecuted instantiation: QuantLib::SviInterpolatedSmileSection::SviInterpolatedSmileSection(QuantLib::Date const&, double const&, std::__1::vector<double, std::__1::allocator<double> > const&, bool, double const&, std::__1::vector<double, std::__1::allocator<double> > const&, double, double, double, double, double, bool, bool, bool, bool, bool, bool, boost::shared_ptr<QuantLib::EndCriteria>, boost::shared_ptr<QuantLib::OptimizationMethod>, QuantLib::DayCounter const&)
Unexecuted instantiation: QuantLib::SviInterpolatedSmileSection::SviInterpolatedSmileSection(QuantLib::Date const&, double const&, std::__1::vector<double, std::__1::allocator<double> > const&, bool, double const&, std::__1::vector<double, std::__1::allocator<double> > const&, double, double, double, double, double, bool, bool, bool, bool, bool, bool, boost::shared_ptr<QuantLib::EndCriteria>, boost::shared_ptr<QuantLib::OptimizationMethod>, QuantLib::DayCounter const&)
96
97
0
void SviInterpolatedSmileSection::createInterpolation() const {
98
0
    ext::shared_ptr<SviInterpolation> tmp(new SviInterpolation(
99
0
        actualStrikes_.begin(), actualStrikes_.end(), vols_.begin(),
100
0
        exerciseTime(), forwardValue_, a_, b_, sigma_, rho_, m_, isAFixed_,
101
0
        isBFixed_, isSigmaFixed_, isRhoFixed_, isMFixed_, vegaWeighted_,
102
0
        endCriteria_, method_));
103
0
    swap(tmp, sviInterpolation_);
104
0
}
105
106
0
void SviInterpolatedSmileSection::performCalculations() const {
107
0
    forwardValue_ = forward_->value();
108
0
    vols_.clear();
109
0
    actualStrikes_.clear();
110
    // we populate the volatilities, skipping the invalid ones
111
0
    for (Size i = 0; i < volHandles_.size(); ++i) {
112
0
        if (volHandles_[i]->isValid()) {
113
0
            if (hasFloatingStrikes_) {
114
0
                actualStrikes_.push_back(forwardValue_ + strikes_[i]);
115
0
                vols_.push_back(atmVolatility_->value() +
116
0
                                volHandles_[i]->value());
117
0
            } else {
118
0
                actualStrikes_.push_back(strikes_[i]);
119
0
                vols_.push_back(volHandles_[i]->value());
120
0
            }
121
0
        }
122
0
    }
123
    // we are recreating the sabrinterpolation object unconditionnaly to
124
    // avoid iterator invalidation
125
0
    createInterpolation();
126
0
    sviInterpolation_->update();
127
0
}
128
129
0
Real SviInterpolatedSmileSection::varianceImpl(Real strike) const {
130
0
    calculate();
131
0
    Real v = (*sviInterpolation_)(strike, true);
132
0
    return v * v * exerciseTime();
133
0
}
134
}