Samedi 18 avril 2009 6 18 /04 /Avr /2009 18:11
- Publié dans : Programmation AS3

Voici l'implémentation du modèle binomial. L'arbre recombinant fait l'objet d'une procédure itérative calibrée pour converger vers le modèle de Black&Scholes pour un pas de 160 environ.

package fx.bidesign.maths
{
    import fx.bidesign.maths.Combination;
    import fx.bidesign.maths.ProbabilityTools;

    public class CoxRossRubinstein
    {

        public function CoxRossRubinstein()
        {

        }
        // (sous-jacent, prix d'exercice, jours restant, volatilté, taux sans risque, dividende, parité)
        public static function value( s:Number, k:Number, t:Number, v:Number, r:Number, c:Number, steps:Number, p:Number = 1 ):Array
        {
            t = t / steps;
            // 1 - q = ( u - Math.exp( ( r - c ) * t ) ) / ( u - d )
            var d:Number = Math.exp( - v * Math.sqrt( t ) );
            var u:Number = Math.exp( v * Math.sqrt( t ) );
            var q:Number = ( Math.exp( ( r - c ) * t ) - d ) / ( u - d );
           
            var call:Number = 0;
           
            for( var i:int = 0; i < steps + 1; i++ )
            {
                call += Combination.evaluate( steps, i ) * Math.pow( q, i ) * Math.pow( 1 - q, steps - i ) * Math.max( s * Math.pow( u, i ) * Math.pow( d, steps - i ) - k, 0 );
            }
           
            var put:Number = 0;
           
            for( var j:int = 0; j < steps + 1; j++ )
            {
                put += Combination.evaluate( steps, j ) * Math.pow( q, j ) * Math.pow( 1 - q, steps - j ) * Math.max( k - ( s * Math.pow( u, j ) * Math.pow( d, steps - j ) ), 0 );
            }

            return [call / p, put / p ];
        }
        // (sous-jacent, prix d'exercice, jours restant, volatilté, taux sans risque, dividende, parité)
        public static function delta( s:Number, k:Number, t:Number, v:Number, r:Number, c:Number, p:Number = 1 ):Array
        {
            var d1:Number = ( Math.log( s / k ) + ( r + Math.pow( v, 2 ) / 2 ) * t ) / ( v * Math.sqrt( t ) );
            var d2:Number = d1 - ( v * Math.sqrt( t ) );

            var call:Number = Math.exp( -  c * t) * ProbabilityTools.normalDistribution( d1 );
            var put:Number = Math.exp( - c * t ) * ( ProbabilityTools.normalDistribution( d1 ) - 1 );

            return [call * 100, put * 100];
        }
        // (sous-jacent, prix d'exercice, jours restant, volatilté, taux sans risque, dividende, parité)
        public static function gamma( s:Number, k:Number, t:Number, v:Number, r:Number, c:Number, p:Number = 1 ):Array
        {
            var d1:Number = ( Math.log( s / k ) + ( r + Math.pow( v, 2 ) / 2 ) * t ) / ( v * Math.sqrt( t ) );
            var d2:Number = d1 - ( v * Math.sqrt( t ) );

            var call:Number = Math.exp( - c * t ) * ( ProbabilityTools.normalDensity( d1 ) / ( s * v * Math.sqrt( t ) ) );
            var put:Number = call;

            return [call / ( p / 100 ), put / ( p / 100 )];
        }
        // (sous-jacent, prix d'exercice, jours restant, volatilté, taux sans risque, dividende, prime du put ou du call, parité)
        public static function theta( s:Number, k:Number, t:Number, v:Number, r:Number, c:Number, fv:Number, p:Number = 1 ):Array
        {
            var d1:Number = ( Math.log( s / k ) + ( r + Math.pow( v, 2 ) / 2 ) * t ) / ( v * Math.sqrt( t ) );
            var d2:Number = d1 - ( v * Math.sqrt( t ) );
    
            var call:Number = - Math.exp( - c * t ) * s * ProbabilityTools.normalDensity( d1 ) * v / ( 2 * Math.sqrt( t ) );
            call += - r * k * Math.exp( - r * t ) * ProbabilityTools.normalDistribution( d2 );
            call += c * s * Math.exp( - c * t ) * ProbabilityTools.normalDistribution( d1 );
           
            var put:Number = - ( s * Math.exp( - c * t ) * v ) / ( 2 * Math.sqrt( t ) ) * ProbabilityTools.normalDensity( d1 );
            put += + r * k * Math.exp( -r * t ) * ( 1 - ProbabilityTools.normalDistribution( d2 ) );
            put += - c * s * Math.exp( - c * t) * ProbabilityTools.normalDistribution( 1 - d1 );
            return [call / 52 / fv * 100, put / 52 / fv * 100];
        }
        // (sous-jacent, prix d'exercice, jours restant, volatilté, taux sans risque, dividende, prime du put ou du call, parité)
        public static function rho( s:Number, k:Number, t:Number, v:Number, r:Number, c:Number, fv:Number, p:Number = 1 ):Array
        {
            var d1:Number = ( Math.log( s / k ) + ( r + Math.pow( v, 2 ) / 2 ) * t ) / ( v * Math.sqrt( t ) );
            var d2:Number = d1 - ( v * Math.sqrt( t ) );

            var call:Number = k * t * Math.exp( - r * t ) * ProbabilityTools.normalDistribution( d2 );
            var put:Number = k * t * Math.exp( - r * t ) * ( ProbabilityTools.normalDistribution( d2 ) - 1 );

            return [call / fv, put / fv];
        }
        // (sous-jacent, prix d'exercice, jours restant, volatilté, taux sans risque, dividende, prime du put ou du call, parité)
        public static function vega( s:Number, k:Number, t:Number, v:Number, r:Number, c:Number, fv:Number, p:Number = 1 ):Array
        {
            var d1:Number = ( Math.log( s / k ) + ( r + Math.pow( v, 2 ) / 2 ) * t ) / ( v * Math.sqrt( t ) );
            var d2:Number = d1 - ( v * Math.sqrt( t ) );

            var call:Number = s * Math.exp(- c * t ) * ProbabilityTools.normalDensity( d1 ) * Math.sqrt( t );
            var put:Number = call;

            return [call / fv, put / fv];
        }
        // (sous-jacent, valeur du delta, prime du put ou du call)
        public static function elasticity( s:Number, del:Number, fv:Number ):Array
        {
            var call:Number = s * del / fv;
            var put:Number = s * del / fv;

            return [call / 100, put / 100];
        }
    }
}


Les grecs sont calculés sur le modèle de Black&Scholes mais à l'occasion je mettrais à jour la classe avec les grecs binomiaux. Le pricer sera également mis à jour pour prendre en charge le modèle binomial.

Par Gilles De Truchis
Ecrire un commentaire - Voir les 0 commentaires
Samedi 18 avril 2009 6 18 /04 /Avr /2009 12:38
- Publié dans : Programmation AS3

Après avoir présenté le modèle de Black, Scholes et Merton, et avoir proposé une implémentation du modèle, voici une application flash utilisant les classes précédemment mises en ligne. Vous remarquerez qu'elles diffèrent légèrement du modèle formalisé puisque, d'un part on a ajouté la parité, et d'autre part, on a calibré l'application sur les warrants et les pricer de warrant en ligne tel que ceux de Boursorama ou Fortunéo. Les valeurs des grecs ne sont pas toujours identiques car selon les pratiques, certains pricer ramènent le theta en variations hebdomadaires ou journalières par exemple. Cette application comprend également un petit convertisseur de date afin de faciliter le calcul du "Time to Maturity". Voici la classe en question:


package fx.bidesign.utils
{
    
    public class DateConverter
    {
        public function DateConverter()
        {
           
        }
        // cDate = [dd, mm, yyyy]
        public static function evaluate( cDate:Array, mDate:Array ):Number
        {
            var beg:Date = new Date( Number( cDate[2] ), Number( cDate[1] ) - 1, Number( cDate[0] ) );
           
            var end:Date = new Date( Number( mDate[2] ), Number( mDate[1] ) - 1, Number( mDate[0] ) );
           
            var pitch:Number = Math.floor( ( end.getTime() - beg.getTime() ) / 1000 / 3600 / 24 );
           
            return pitch;
        }
    }
}


Vous trouverez également dans les sources, une classe pour pricer des contrats Forward, toujours pour des sous-jacents type action:

package fx.bidesign.maths
{
    import fx.bidesign.maths.Factorial;
    
    public class Forward
    {

        public function Forward()
        {

        }
        public static function evaluate( k:Number, s:Number, r:Number, t:Number, q:Number ):Array
        {
            var f1:Number = s * Math.exp( - q * t ) * Math.exp( r * t );
            var f2:Number = ( f1 - k ) * Math.exp( - r * t );
           
            return [f1, f2];
        }
    }
}



Et voici le pricer:

Par Gilles De Truchis
Ecrire un commentaire - Voir les 0 commentaires

Un problème d'affichage...?

Certaines pages de ce site contiennent des animations Flash qui nécessitent la dernière version du flash player.

haut de page

Varennes EcoFin

Mon site internet migre vers une nouvelle adresse: Varennes EcoFin. Il s'agit d'un site en flash recentré sur mes travaux de recherches, ma thèse et des resources pour les étudiants (programmes, bases de données etc.). Pour accéder à la version sans flash (HTML5): Varennes EcoFin Sky.

Présentation

Bienvenue

Bienvenue sur Ceteris Paribus... Ce site traite d'actualité économique, d'économétrie,  de macroéconomie, de finance, mais également de programmation Flash (actionscript 3). Vous y trouverez donc, entre autres, des ressources informatiques pour des applications financières, mais également des articles techniques sur divers modèles économétriques, financiers et macroéconomiques.

Note: Certaines pages de ce site contiennent des animations Flash qui nécessitent la dernière version du flash player.

En préparation...

Modèle de regime-switching: Volatility-switching et non-linearité.
VAR structurels et restriction par hétéroscedasticité.
Modèle Markov-Switching ARFIMA

Recherche

 
Créer un blog gratuit sur over-blog.com - Contact - C.G.U. - Signaler un abus - Articles les plus commentés