예제 #1
0
        public void testMonteCarloLookback()
        {
            double tolerance = 0.1;

            DayCounter dc    = new Actual360();
            Date       today = Date.Today;

            double strike = 90;
            double t      = 1;
            double t1     = 0.25;

            Date     exDate   = today + Convert.ToInt32(t * 360 + 0.5);
            Exercise exercise = new EuropeanExercise(exDate);

            SimpleQuote           spot  = new SimpleQuote(0.0);
            SimpleQuote           qRate = new SimpleQuote(0.0);
            YieldTermStructure    qTS   = Utilities.flatRate(today, qRate, dc);
            SimpleQuote           rRate = new SimpleQuote(0.0);
            YieldTermStructure    rTS   = Utilities.flatRate(today, rRate, dc);
            SimpleQuote           vol   = new SimpleQuote(0.0);
            BlackVolTermStructure volTS = Utilities.flatVol(today, vol, dc);

            spot.setValue(100);
            qRate.setValue(0);
            rRate.setValue(0.06);
            vol.setValue(0.1);

            BlackScholesMertonProcess stochProcess =
                new BlackScholesMertonProcess(
                    new Handle <Quote>(spot),
                    new Handle <YieldTermStructure>(qTS),
                    new Handle <YieldTermStructure>(rTS),
                    new Handle <BlackVolTermStructure>(volTS));

            Option.Type[] types = new Option.Type[] { Option.Type.Call, Option.Type.Put };

            for (int i = 0; i < types.Length; i++)
            {
                Option.Type type = types[i];

                StrikedTypePayoff payoff = new PlainVanillaPayoff(type, strike);

                /**
                 * Partial Fixed
                 * **/

                Date lookbackStart = today + Convert.ToInt32(t1 * 360 + 0.5);
                ContinuousPartialFixedLookbackOption partialFixedLookback
                    = new ContinuousPartialFixedLookbackOption(lookbackStart,
                                                               payoff,
                                                               exercise);
                IPricingEngine engine =
                    new AnalyticContinuousPartialFixedLookbackEngine(stochProcess);

                partialFixedLookback.setPricingEngine(engine);

                double analytical = partialFixedLookback.NPV();

                IPricingEngine mcpartialfixedengine =
                    new MakeMCLookbackEngine <ContinuousPartialFixedLookbackOption.Arguments, ContinuousPartialFixedLookbackOption.Results,
                                              PseudoRandom, Statistics>(stochProcess)
                    .withSteps(2000)
                    .withAntitheticVariate()
                    .withSeed(1)
                    .withAbsoluteTolerance(tolerance)
                    .value();

                partialFixedLookback.setPricingEngine(mcpartialfixedengine);
                double monteCarlo = partialFixedLookback.NPV();

                double diff = Math.Abs(analytical - monteCarlo);

                if (diff > tolerance)
                {
                    REPORT_FAILURE_MC("Partial Fixed", type, analytical, monteCarlo, tolerance);
                }

                /**
                 * Fixed
                 * **/

                double minMax = 100;

                ContinuousFixedLookbackOption fixedLookback
                    = new ContinuousFixedLookbackOption(minMax,
                                                        payoff,
                                                        exercise);
                IPricingEngine analyticalfixedengine =
                    new AnalyticContinuousFixedLookbackEngine(stochProcess);

                fixedLookback.setPricingEngine(analyticalfixedengine);
                analytical = fixedLookback.NPV();

                IPricingEngine mcfixedengine =
                    new MakeMCLookbackEngine <ContinuousFixedLookbackOption.Arguments, ContinuousFixedLookbackOption.Results,
                                              PseudoRandom, Statistics>(stochProcess)
                    .withSteps(2000)
                    .withAntitheticVariate()
                    .withSeed(1)
                    .withAbsoluteTolerance(tolerance)
                    .value();

                fixedLookback.setPricingEngine(mcfixedengine);
                monteCarlo = fixedLookback.NPV();

                diff = Math.Abs(analytical - monteCarlo);

                if (diff > tolerance)
                {
                    REPORT_FAILURE_MC("Fixed", type, analytical, monteCarlo, tolerance);
                }

                /**
                 * Partial Floating
                 * **/

                double lambda      = 1;
                Date   lookbackEnd = today + Convert.ToInt32(t1 * 360 + 0.5);

                FloatingTypePayoff floatingPayoff = new FloatingTypePayoff(type);

                ContinuousPartialFloatingLookbackOption partialFloating
                    = new ContinuousPartialFloatingLookbackOption(minMax,
                                                                  lambda,
                                                                  lookbackEnd,
                                                                  floatingPayoff,
                                                                  exercise);
                IPricingEngine analyticalpartialFloatingengine =
                    new AnalyticContinuousPartialFloatingLookbackEngine(stochProcess);
                partialFloating.setPricingEngine(analyticalpartialFloatingengine);

                analytical = partialFloating.NPV();

                IPricingEngine mcpartialfloatingengine =
                    new MakeMCLookbackEngine <ContinuousPartialFloatingLookbackOption.Arguments, ContinuousPartialFloatingLookbackOption.Results,
                                              PseudoRandom, Statistics>
                        (stochProcess)
                    .withSteps(2000)
                    .withAntitheticVariate()
                    .withSeed(1)
                    .withAbsoluteTolerance(tolerance)
                    .value();

                partialFloating.setPricingEngine(mcpartialfloatingengine);
                monteCarlo = partialFloating.NPV();

                diff = Math.Abs(analytical - monteCarlo);

                if (diff > tolerance)
                {
                    REPORT_FAILURE_MC("Partial Floating", type, analytical, monteCarlo, tolerance);
                }

                /**
                 * Floating
                 * **/

                ContinuousFloatingLookbackOption floating =
                    new ContinuousFloatingLookbackOption(minMax,
                                                         floatingPayoff,
                                                         exercise);
                IPricingEngine analyticalFloatingengine =
                    new AnalyticContinuousFloatingLookbackEngine(stochProcess);
                floating.setPricingEngine(analyticalFloatingengine);

                analytical = floating.NPV();

                IPricingEngine mcfloatingengine =
                    new MakeMCLookbackEngine <ContinuousFloatingLookbackOption.Arguments, ContinuousFloatingLookbackOption.Results,
                                              PseudoRandom, Statistics>
                        (stochProcess)
                    .withSteps(2000)
                    .withAntitheticVariate()
                    .withSeed(1)
                    .withAbsoluteTolerance(tolerance)
                    .value();

                floating.setPricingEngine(mcfloatingengine);
                monteCarlo = floating.NPV();

                diff = Math.Abs(analytical - monteCarlo);

                if (diff > tolerance)
                {
                    REPORT_FAILURE_MC("Floating", type, analytical, monteCarlo, tolerance);
                }
            }
        }
예제 #2
0
        public void testAnalyticContinuousPartialFloatingLookback()
        {
            // Testing analytic continuous partial floating-strike lookback options...");
            LookbackOptionData[] values =
            {
                // data from "Option Pricing Formulas, Second Edition", Haug, 2006, pg.146

                //type,         strike, minmax, s,    q,    r,    t,    v,    l,  t1,     result,   tol
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.1, 1, 0.25,  8.6524, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.1, 1,  0.5,  9.2128, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.1, 1, 0.75,  9.5567, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.1, 1, 0.25, 10.5751, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.1, 1,  0.5, 11.2601, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.1, 1, 0.75, 11.6804, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.2, 1, 0.25, 13.3402, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.2, 1,  0.5, 14.5121, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.2, 1, 0.75,  15.314, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.2, 1, 0.25, 16.3047, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.2, 1,  0.5,  17.737, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.2, 1, 0.75, 18.7171, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.3, 1, 0.25, 17.9831, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.3, 1,  0.5, 19.6618, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0,  90,  90, 0, 0.06, 1, 0.3, 1, 0.75, 20.8493, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.3, 1, 0.25, 21.9793, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.3, 1,  0.5, 24.0311, 1.0e-4),
                new LookbackOptionData(Option.Type.Call, 0, 110, 110, 0, 0.06, 1, 0.3, 1, 0.75, 25.4825, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.1, 1, 0.25,  2.7189, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.1, 1,  0.5,  3.4639, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.1, 1, 0.75,  4.1912, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.1, 1, 0.25,  3.3231, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.1, 1,  0.5,  4.2336, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.1, 1, 0.75,  5.1226, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.2, 1, 0.25,  7.9153, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.2, 1,  0.5,  9.5825, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.2, 1, 0.75, 11.0362, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.2, 1, 0.25,  9.6743, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.2, 1,  0.5, 11.7119, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.2, 1, 0.75, 13.4887, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.3, 1, 0.25, 13.4719, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.3, 1,  0.5, 16.1495, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0,  90,  90, 0, 0.06, 1, 0.3, 1, 0.75, 18.4071, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.3, 1, 0.25, 16.4657, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.3, 1,  0.5, 19.7383, 1.0e-4),
                new LookbackOptionData(Option.Type.Put,  0, 110, 110, 0, 0.06, 1, 0.3, 1, 0.75, 22.4976, 1.0e-4)
            };

            DayCounter dc    = new Actual360();
            Date       today = Date.Today;

            SimpleQuote           spot  = new SimpleQuote(0.0);
            SimpleQuote           qRate = new SimpleQuote(0.0);
            YieldTermStructure    qTS   = Utilities.flatRate(today, qRate, dc);
            SimpleQuote           rRate = new SimpleQuote(0.0);
            YieldTermStructure    rTS   = Utilities.flatRate(today, rRate, dc);
            SimpleQuote           vol   = new SimpleQuote(0.0);
            BlackVolTermStructure volTS = Utilities.flatVol(today, vol, dc);

            for (int i = 0; i < values.Length; i++)
            {
                Date     exDate   = today + Convert.ToInt32(values[i].t * 360 + 0.5);
                Exercise exercise = new EuropeanExercise(exDate);

                spot.setValue(values[i].s);
                qRate.setValue(values[i].q);
                rRate.setValue(values[i].r);
                vol.setValue(values[i].v);

                FloatingTypePayoff payoff = new FloatingTypePayoff(values[i].type);

                BlackScholesMertonProcess stochProcess = new BlackScholesMertonProcess(
                    new Handle <Quote>(spot),
                    new Handle <YieldTermStructure>(qTS),
                    new Handle <YieldTermStructure>(rTS),
                    new Handle <BlackVolTermStructure>(volTS));

                IPricingEngine engine = new AnalyticContinuousPartialFloatingLookbackEngine(stochProcess);

                Date lookbackEnd = today + Convert.ToInt32(values[i].t1 * 360 + 0.5);
                ContinuousPartialFloatingLookbackOption option = new ContinuousPartialFloatingLookbackOption(
                    values[i].minmax, values[i].l, lookbackEnd, payoff, exercise);
                option.setPricingEngine(engine);

                double calculated = option.NPV();
                double expected   = values[i].result;
                double error      = Math.Abs(calculated - expected);
                if (error > values[i].tol)
                {
                    REPORT_FAILURE_FLOATING("value", values[i].minmax, payoff,
                                            exercise, values[i].s, values[i].q,
                                            values[i].r, today, values[i].v,
                                            expected, calculated, error,
                                            values[i].tol);
                }
            }
        }