def test_repr(self): hedger = Hedger(Linear(2, 1), ["moneyness", "expiry_time"]) assert repr(hedger) == ( "Hedger(\n" " features=['moneyness', 'expiry_time'],\n" " (model): Linear(in_features=2, out_features=1, bias=True)\n" " (criterion): EntropicRiskMeasure()\n" ")") liability = EuropeanOption(BrownianStock()) model = BlackScholes(liability) hedger = Hedger(model, model.features()) assert repr(hedger) == ( "Hedger(\n" " features=['log_moneyness', 'expiry_time', 'volatility'],\n" " (model): BSEuropeanOption()\n" " (criterion): EntropicRiskMeasure()\n" ")") hedger = Hedger(naked, ["moneyness", "expiry_time"]) assert repr(hedger) == ("Hedger(\n" " model=naked,\n" " features=['moneyness', 'expiry_time'],\n" " (criterion): EntropicRiskMeasure()\n" ")")
def test_shape(self): torch.distributions.Distribution.set_default_validate_args(False) deriv = EuropeanOption(BrownianStock()) N = 2 M_1 = 5 M_2 = 6 H_in = 3 x = torch.empty((N, M_1, M_2, H_in)) m = Hedger(MultiLayerPerceptron(), ["zero"]) assert m(x).size() == torch.Size((N, M_1, M_2, 1)) model = BlackScholes(deriv) m = Hedger(model, model.features()) x = torch.empty((N, M_1, M_2, len(model.features()))) assert m(x).size() == torch.Size((N, M_1, M_2, 1)) model = WhalleyWilmott(deriv) m = Hedger(model, model.features()) x = torch.empty((N, M_1, M_2, len(model.features()))) assert m(x).size() == torch.Size((N, M_1, M_2, 1)) model = Naked() m = Hedger(model, ["zero"]) x = torch.empty((N, M_1, M_2, 10)) assert m(x).size() == torch.Size((N, M_1, M_2, 1))
def test_compute_loss(self): torch.manual_seed(42) deriv = EuropeanOption(BrownianStock()) hedger = Hedger(Naked(), ["log_moneyness", "expiry_time", "volatility"]) result = hedger.compute_loss(deriv) expect = EntropicRiskMeasure()(-deriv.payoff()) assert torch.allclose(result, expect)
def test_example(self): from pfhedge import Hedger from pfhedge.instruments import BrownianStock from pfhedge.instruments import EuropeanOption liability = EuropeanOption(BrownianStock()) model = BSEuropeanOption() hedger = Hedger(model, model.features()) price = hedger.price(liability) assert torch.allclose(price, torch.tensor(0.0221), atol=1e-4)
def test_example(self): from pfhedge import Hedger from pfhedge.instruments import BrownianStock from pfhedge.instruments import LookbackOption deriv = LookbackOption(BrownianStock(), strike=1.03) model = BSLookbackOption(deriv) hedger = Hedger(model, model.features()) price = hedger.price(deriv) assert torch.allclose(price, torch.tensor(0.0177), atol=1e-4)
def test_example(self): from pfhedge import Hedger from pfhedge.instruments import BrownianStock from pfhedge.instruments import EuropeanBinaryOption deriv = EuropeanBinaryOption(BrownianStock()) model = BSEuropeanBinaryOption(deriv) hedger = Hedger(model, model.features()) price = hedger.price(deriv) assert torch.allclose(price, torch.tensor(0.5004), atol=1e-4)
def test_example(self): from pfhedge import Hedger from pfhedge.instruments import AmericanBinaryOption from pfhedge.instruments import BrownianStock deriv = AmericanBinaryOption(BrownianStock(), strike=1.03) model = BSAmericanBinaryOption(deriv) hedger = Hedger(model, model.features()) price = hedger.price(deriv) assert torch.allclose(price, torch.tensor(0.6219), atol=1e-4)
def test_compute_pnl(self): torch.manual_seed(42) deriv = EuropeanOption(BrownianStock()) hedger = Hedger(Naked(), ["zero"]) pnl = hedger.compute_pnl(deriv) payoff = deriv.payoff() assert torch.allclose(pnl, -payoff) result = hedger.compute_pnl(deriv) expect = -deriv.payoff() assert torch.allclose(result, expect)
def test(self, volatility): torch.manual_seed(42) liability = EuropeanOption(BrownianStock(volatility)) liability.underlier.prices = torch.arange(1.0, 7.0).reshape(3, 2) hedger = Hedger(Linear(2, 1), ["moneyness", "expiry_time"]) hedger.features = [ feature.of(liability) for feature in hedger.features ] f = PrevHedge().of(liability, hedger) result = f[0] expect = torch.zeros((2, 1)) assert torch.allclose(result, expect) h = hedger(torch.cat([feature[0] for feature in hedger.features], 1)) result = f[1] expect = h.reshape(-1, 1) assert torch.allclose(result, expect) h = hedger(torch.cat([feature[1] for feature in hedger.features], 1)) result = f[2] expect = h.reshape(-1, 1) assert torch.allclose(result, expect)
def test_net(): liability = EuropeanOption(BrownianStock(cost=1e-4)) model = MultiLayerPerceptron() hedger = Hedger(model, ["log_moneyness", "expiry_time", "volatility", "prev_hedge"]) _ = hedger.fit(liability, n_paths=100, n_epochs=10) _ = hedger.price(liability)
def test_ww(): liability = EuropeanOption(BrownianStock(cost=1e-4)) model = WhalleyWilmott(liability) hedger = Hedger(model, model.features()) _ = hedger.price(liability)
def test_bs(): liability = EuropeanOption(BrownianStock(cost=1e-4)) model = BlackScholes(liability) hedger = Hedger(model, model.features()) _ = hedger.price(liability)
# Example to use a multi-layer perceptron as a hedging model import sys import torch sys.path.append("..") from pfhedge import Hedger # noqa: E402 from pfhedge.instruments import BrownianStock # noqa: E402 from pfhedge.instruments import EuropeanOption # noqa: E402 from pfhedge.nn import MultiLayerPerceptron # noqa: E402 if __name__ == "__main__": torch.manual_seed(42) # Prepare a derivative to hedge deriv = EuropeanOption(BrownianStock(cost=1e-4)) # Create your hedger model = MultiLayerPerceptron() hedger = Hedger(model, ["log_moneyness", "expiry_time", "volatility", "prev_hedge"]) # Fit and price hedger.fit(deriv, n_paths=10000, n_epochs=200) price = hedger.price(deriv, n_paths=10000) print(f"Price={price:.5e}")
# Example to use Black-Scholes' delta-hedging strategy as a hedging model import sys import torch sys.path.append("..") from pfhedge import Hedger # noqa: E402 from pfhedge.instruments import BrownianStock # noqa: E402 from pfhedge.instruments import EuropeanOption # noqa: E402 from pfhedge.nn import BlackScholes # noqa: E402 if __name__ == "__main__": torch.manual_seed(42) # Prepare a derivative to hedge deriv = EuropeanOption(BrownianStock(cost=1e-4)) # Create your hedger model = BlackScholes(deriv) hedger = Hedger(model, model.features()) # Fit and price price = hedger.price(deriv, n_paths=10000) print(f"Price={price:.5e}")
from pfhedge.features import ExpiryTime # noqa: E402 from pfhedge.features import Volatility # noqa: E402 from pfhedge.features import ModuleOutput # noqa: E402 from pfhedge.instruments import BrownianStock # noqa: E402 from pfhedge.instruments import EuropeanOption # noqa: E402 from pfhedge.nn import BlackScholes # noqa: E402 from pfhedge.nn import MultiLayerPerceptron # noqa: E402 if __name__ == "__main__": torch.manual_seed(42) # Prepare a derivative to hedge deriv = EuropeanOption(BrownianStock(cost=1e-4)) # bs is a module that outputs Black-Scholes' delta bs = BlackScholes(deriv) delta = ModuleOutput(bs, features=[LogMoneyness(), ExpiryTime(), Volatility()]) # Create your hedger # Here `delta` is a feature that outputs Black-Scholes' delta model = MultiLayerPerceptron() hedger = Hedger(model, [delta, "prev_hedge"]) # Fit and price hedger.fit(deriv, n_paths=10000, n_epochs=200) price = hedger.price(deriv, n_paths=10000) print(f"Price={price:.5e}")
stock = BrownianStock(cost=1e-4) deriv = EuropeanOption(stock) print(">>> stock") print_as_comment(stock) print(">>> deriv") print_as_comment(deriv) # --- Fit and price from pfhedge import Hedger from pfhedge.nn import MultiLayerPerceptron model = MultiLayerPerceptron() hedger = Hedger(model, ["log_moneyness", "expiry_time", "volatility", "prev_hedge"]) hedger print(">>> hedger") print_as_comment(hedger) hedger.fit(deriv) price = hedger.price(deriv) print(">>> price") print_as_comment(price) # --- Black-Scholes and Whalley-Wilmott from pfhedge.nn import BlackScholes from pfhedge.nn import WhalleyWilmott
sys.path.append("..") from pfhedge import Hedger # noqa: E402 from pfhedge.instruments import BrownianStock # noqa: E402 from pfhedge.instruments import EuropeanOption # noqa: E402 from pfhedge.nn import ExpectedShortfall from pfhedge.nn import MultiLayerPerceptron # noqa: E402 if __name__ == "__main__": torch.manual_seed(42) # Prepare a derivative to hedge deriv = EuropeanOption(BrownianStock(cost=1e-4)) # Expected shortfall with the quantile level of 10% expected_shortfall = ExpectedShortfall(0.1) # Create your hedger model = MultiLayerPerceptron() hedger = Hedger( model, ["log_moneyness", "expiry_time", "volatility", "prev_hedge"], criterion=expected_shortfall, ) # Fit and price hedger.fit(deriv, n_paths=10000, n_epochs=200) price = hedger.price(deriv, n_paths=10000) print(f"Price={price:.5e}")
def test_error_optimizer(self): hedger = Hedger(Linear(2, 1), ["moneyness", "expiry_time"]) liability = EuropeanOption(BrownianStock()) with pytest.raises(TypeError): hedger.fit(liability, optimizer=Identity)