L'abbaye de Thélème

Œconomicon, l'atelier d'économie

Œconomicon

Le concept

L'Œconomicon est mon grimoire d'économie : un atelier où les grands modèles, prototypés sous MATLAB puis recodés en JavaScript, prennent vie et se laissent manipuler dans votre navigateur. L'idée n'est pas de suivre les cours en Bourse, mais de comprendre les ressorts de l'économie et des marchés. Tout en bas, une salle des marchés en direct vous attend, en bonus.

Géoéconomie

L'économie comme instrument de puissance : dépendances, sanctions, énergie, monnaie.

Les leviers de la puissance économique

La géoéconomie étudie l'économie employée comme moyen d'action politique. Un État ne dispose pas seulement d'une armée et d'une diplomatie : il peut ouvrir ou fermer un marché, couper une ressource, exclure d'un système de paiement ou refuser une technologie. Voici les principaux leviers, ceux qui reviennent le plus souvent dans l'actualité.

Dépendance commerciale

Quand un pays écoule l'essentiel de sa production chez un seul client, ce client détient un moyen de pression.

Énergie

Le gaz et le pétrole se coupent comme un robinet : l'acheteur dépendant paie son chauffage en concessions.

Matières premières critiques

Terres rares, lithium, semi-conducteurs : quelques pays contrôlent des maillons sans substitut immédiat.

Monnaie et finance

Émettre la monnaie des échanges permet de geler des avoirs et d'exclure des banques du système de paiement.

Technologie et normes

Contrôler les exportations de machines ou imposer ses standards, c'est décider qui peut produire quoi.

Infrastructures

Ports, câbles sous-marins, corridors : financer une infrastructure, c'est s'installer durablement sur une route.

Dépendance asymétrique : qui tient l'autre ?

L'interdépendance est rarement équilibrée, et c'est justement le déséquilibre qui crée le pouvoir. On distingue la sensibilité (le poids brut de la relation) de la vulnérabilité (ce qu'il en reste une fois cherchées des solutions de rechange). Un pays très exposé mais capable de retrouver d'autres partenaires est finalement peu vulnérable. Déplacez les curseurs : la part des exportations dirigée vers l'autre, puis la facilité à se réorienter. Le levier revient au moins vulnérable des deux.

Voir le code MATLAB
% Dependance asymetrique : sensibilite (brut) vs vulnerabilite (net)
da = 0.30; sa = 0.30;   % A : part exportee vers B, capacite de reorientation
db = 0.08; sb = 0.60;   % B : part exportee vers A, capacite de reorientation
vA = da * (1 - sa);     % vulnerabilite de A (ce qui reste apres reorientation)
vB = db * (1 - sb);     % vulnerabilite de B
asym = (vA - vB) * 100; % asymetrie, en points de pourcentage

figure;
M = [da*100 vA*100; db*100 vB*100];   % lignes = pays, colonnes = [sensibilite vulnerabilite]
hb = bar(M);
hb(1).FaceColor = [0.85 0.75 0.45];
hb(2).FaceColor = [0.18 0.43 0.70];
set(gca, 'XTickLabel', {'Pays A', 'Pays B'});
ylabel('Part des exportations (%)');
legend('Sensibilite (brut)', 'Vulnerabilite (net)', 'Location', 'northeast');
title(sprintf('Le levier revient au moins vulnerable  (asymetrie %+.0f pts)', asym));
grid on;

La guerre commerciale (théorie des jeux)

Deux économies, un choix chacune : ouvrir ses frontières (libre-échange) ou taxer les importations (tarifs). La matrice donne les gains de chaque camp selon les quatre combinaisons. Déplacez les curseurs et observez l'équilibre de Nash (bordure rouge : la case où aucun pays n'a intérêt à changer seul de stratégie). Le plus souvent, chacun a intérêt à taxer, et les deux finissent perdants alors que le libre-échange mutuel aurait été meilleur pour tous.

Voir le code MATLAB
% Guerre commerciale : dilemme du prisonnier (2 pays, 2 choix)
R = 3; T = 5; P = 1; S = 0;   % gains : Reward, Temptation, Punishment, Sucker
A = [R S; T P];               % gains du pays A (lignes A = ouvrir / taxer)
B = [R T; S P];               % gains du pays B (colonnes B = ouvrir / taxer)
tot = A + B;                  % bien-etre total par case

figure; imagesc(tot); colormap(flipud(gray)); hold on;
labels = {'Ouvrir', 'Taxer'};
set(gca, 'XTick', 1:2, 'XTickLabel', labels, 'YTick', 1:2, 'YTickLabel', labels);
xlabel('Choix du pays B'); ylabel('Choix du pays A');
for i = 1:2
  for j = 1:2
    text(j, i, sprintf('A = %d\nB = %d', A(i,j), B(i,j)), ...
         'HorizontalAlignment', 'center', 'FontWeight', 'bold');
  end
end
% Equilibre de Nash : (Taxer, Taxer) des que T > R et P > S
rectangle('Position', [1.5 1.5 1 1], 'EdgeColor', [0.8 0 0], 'LineWidth', 3);
title('Nash = (Taxer, Taxer), alors que (Ouvrir, Ouvrir) serait meilleur pour les deux');

La course aux armements

Deux pays rivaux s'observent : dès que l'un renforce son armée, l'autre suit, par méfiance. Mais l'effort a un coût qui freine chacun (la retenue), et de vieux griefs poussent à s'armer même sans provocation. Ce sont les deux droites de réaction qui décident du sort. Si la retenue l'emporte sur la méfiance, elles se croisent : les arsenaux se stabilisent à un niveau fini (une paix armée). Si la méfiance l'emporte, chaque hausse en appelle une plus grande et les courbes divergent : c'est la course aux armements, la spirale de Richardson. Déplacez la méfiance et la retenue pour basculer d'un régime à l'autre.

Voir le code MATLAB
% Course aux armements (modele de Richardson)
k = 0.6; r = 1.0; g = 5;        % mefiance (reaction), retenue (cout), griefs
% dynamique : dx/dt = k*y - r*x + g ; dy/dt = k*x - r*y + g
% equilibre symetrique x = y = g/(r-k), STABLE si la retenue depasse la mefiance
stable = r > k;
if stable, xeq = g/(r-k); else, xeq = Inf; end

y = linspace(0, max(20, g/r*3), 200);
X = (g + k*y)/r;      % ligne du pays X : r*x = k*y + g
Y = (g + k*y)/r;      % ligne du pays Y (symetrique)

figure; hold on;
plot(X, y, 'LineWidth', 2);      % ligne pays X (axe x = armement de X)
plot(y, Y, 'LineWidth', 2);      % ligne pays Y
if stable, plot(xeq, xeq, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.17 0.17 0.14]); end
xlabel('Armement pays X'); ylabel('Armement pays Y');
legend('Reaction pays X', 'Reaction pays Y', 'Location', 'northwest');
if stable, tt = sprintf('Stable : arsenaux vers %.1f', xeq); else, tt = 'Course aux armements (divergence)'; end
title(tt); grid on;

Le pouvoir de négociation

Un accord crée de la valeur (un contrat gazier, un cessez-le-feu, une coentreprise), mais encore faut-il se partager le gâteau. La théorie du marchandage donne une règle simple : chacun repart d'abord avec son « option de repli » (ce qu'il obtient si les négociations échouent), puis le surplus restant se partage selon le rapport de force. Conséquence clé : celui qui a la meilleure option de repli, celui qui a le moins besoin de l'accord, capte la plus grosse part. C'est le pouvoir de la position de repli (la BATNA). Déplacez les options de repli et le rapport de force : voyez le point de partage glisser le long de la frontière des accords possibles.

Voir le code MATLAB
% Marchandage : partage d'un surplus selon les options de repli
S = 100; d1 = 20; d2 = 20; beta = 0.5;   % taille de l'accord, replis A et B, pouvoir de A
surplus = S - d1 - d2;                    % gain cree par l'accord
if surplus >= 0
  uA = d1 + beta*surplus;                 % part du pays A
  uB = d2 + (1-beta)*surplus;             % part du pays B
else
  uA = d1; uB = d2;                       % pas d'accord : chacun reste a son repli
end

figure; hold on;
fill([d1 S-d2 d1], [d2 d2 S-d1], [0.20 0.45 0.70], 'FaceAlpha', 0.12, 'EdgeColor', 'none');  % accords possibles
plot([S 0], [0 S], 'LineWidth', 2);        % frontiere u1 + u2 = S
plot(d1, d2, 's', 'MarkerSize', 8, 'MarkerFaceColor', [0.55 0.55 0.50]);   % option de repli
plot([d1 uA], [d2 uB], '--');               % du repli au partage
plot(uA, uB, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.17 0.17 0.14]);   % partage retenu
xlabel('Gain du pays A'); ylabel('Gain du pays B');
legend('Accords possibles', 'Frontiere', 'Repli', 'Partage', 'Location', 'northeast');
title(sprintf('Partage : A = %.0f, B = %.0f (surplus %.0f)', uA, uB, surplus));
axis([0 S 0 S]); grid on;

Le coût d'un tarif douanier

Un pays qui importe au prix mondial protège sa production en posant un tarif : le prix intérieur monte, la production locale augmente, la consommation baisse, et les importations se réduisent. Déplacez le prix mondial et le tarif. Le rectangle vert est la recette de l'État ; les triangles orange sont la perte sèche (ce que personne ne récupère). Les producteurs gagnent, mais les consommateurs perdent davantage.

Voir le code MATLAB
% Cout d'un tarif douanier (petite economie ouverte)
Pw = 20; t = 15; s = 1;        % prix mondial, tarif, elasticite de l'offre
Peq = 100/(1+s);               % prix d'autarcie (demande Qd=100-P, offre Qs=s*P)
Pt  = min(Pw+t, Peq);          % prix interieur avec tarif
Qd0 = 100-Pw; Qs0 = s*Pw;      % libre-echange
Qd1 = 100-Pt; Qs1 = s*Pt;      % avec tarif
P = linspace(0, 100, 200);

figure; hold on;
plot(100-P, P, 'LineWidth', 2);                 % demande (Q en abscisse)
plot(s*P,   P, 'LineWidth', 2);                 % offre
fill([Qs1 Qd1 Qd1 Qs1], [Pw Pw Pt Pt], [0.30 0.55 0.35], 'FaceAlpha', 0.35, 'EdgeColor', 'none');  % recette Etat
fill([Qs0 Qs1 Qs1], [Pw Pw Pt], [0.85 0.55 0.20], 'FaceAlpha', 0.45, 'EdgeColor', 'none');          % perte seche (offre)
fill([Qd1 Qd0 Qd1], [Pt Pw Pw], [0.85 0.55 0.20], 'FaceAlpha', 0.45, 'EdgeColor', 'none');          % perte seche (demande)
plot([0 100], [Pw Pw], '--');                   % prix mondial
plot([0 100], [Pt Pt], '-.');                   % prix avec tarif
xlabel('Quantite'); ylabel('Prix'); xlim([0 100]); ylim([0 60]);
legend('Demande', 'Offre', 'Recette de l''Etat', 'Perte seche', 'Location', 'northeast');
title('Tarif douanier : recette de l''Etat (vert) et perte seche (orange)');

L'avantage comparatif (Ricardo)

Deux pays, deux biens (blé et technologie). Même si un pays est meilleur dans les deux, les deux gagnent à se spécialiser là où leur coût d'opportunité est le plus faible, puis à échanger. Déplacez les productivités : la frontière de production mondiale (trait plein) se déforme vers l'extérieur par rapport à la simple addition (pointillé). Cet écart, c'est le gain à l'échange.

Voir le code MATLAB
% Avantage comparatif (Ricardo) : 2 pays, 2 biens (ble, technologie)
p1b = 60; p1t = 120;   % pays 1 : max ble / max tech
p2b = 40; p2t = 30;    % pays 2 : max ble / max tech
oc1 = p1t/p1b; oc2 = p2t/p2b;         % couts d'opportunite du ble
maxBle = p1b + p2b; maxTech = p1t + p2t;
if oc1 <= oc2
  kinkBle = p1b; kinkTech = p2t;      % pays 1 -> ble, pays 2 -> tech
else
  kinkBle = p2b; kinkTech = p1t;
end

figure; hold on;
plot([0 kinkBle maxBle], [maxTech kinkTech 0], 'LineWidth', 2);   % frontiere mondiale (specialisation)
plot([0 maxBle], [maxTech 0], '--');                             % sans specialisation
xlabel('Ble'); ylabel('Technologie');
legend('Frontiere mondiale (specialisation)', 'Sans specialisation', 'Location', 'northeast');
title('Ricardo : le gain a l''echange = ecart entre les deux courbes');
grid on;

Les points d'étranglement

Certaines ressources critiques (terres rares, semi-conducteurs, énergie) sont produites par une poignée de pays. Plus l'offre est concentrée, plus un seul fournisseur peut faire pression en coupant le robinet. Réglez la production de chaque fournisseur : l'indice de concentration (HHI) et la barre montrent qui tient la ressource, et la simulation « et si le premier coupe ? » mesure la part de l'offre qui disparaîtrait d'un coup.

Voir le code MATLAB
% Points d'etranglement : concentration de l'offre (HHI)
q = [50 25 15 10];                 % production de chaque fournisseur
parts = q / sum(q);
hhi = round(sum(parts.^2) * 10000);   % indice Herfindahl-Hirschman
[dominant, idx] = max(parts);         % 1er fournisseur
perteSiCoupe = dominant * 100;        % pourcentage de l'offre perdu s'il coupe

figure; hold on;
bar(parts*100, 'FaceColor', [0.55 0.62 0.72]);
bar(idx, parts(idx)*100, 'FaceColor', [0.80 0.20 0.15]);   % le dominant en rouge
set(gca, 'XTick', 1:numel(q), 'XTickLabel', {'F1','F2','F3','F4'});
xlabel('Fournisseurs'); ylabel('Part de marche (%)');
title(sprintf('HHI = %d   |   si le 1er coupe : -%.0f%% de l''offre', hhi, perteSiCoupe));
grid on;

Le cartel (OPEP)

Des producteurs d'une même ressource peuvent s'entendre pour brider leur offre et faire monter le prix, comme l'OPEP sur le pétrole : ensemble, ils se comportent comme un monopole. Mais chaque membre est tenté de tricher, c'est-à-dire de pomper plus que son quota pour profiter du prix élevé, ce qui finit par le faire retomber. Déplacez le nombre de membres et le coût d'extraction : comparez le prix du cartel à celui de la concurrence, et mesurez le gain à tricher qui mine la discipline.

Voir le code MATLAB
% Cartel (OPEP) : entente vs concurrence, gain a tricher
A = 100; c = 20; N = 6;              % demande P=A-Q, cout c, N membres
Qc = (A-c)/2;   Pcart = (A+c)/2;             % cartel = monopole
Qn = N*(A-c)/(N+1);   Pconc = A - Qn;        % concurrence (Cournot)
share  = (Pcart-c)*(Qc/N);                   % profit par membre
others = (N-1)*Qc/N;                         % les autres tiennent le quota
qDef = (A-c-others)/2;   Pdef = A-(others+qDef);
gain = (Pdef-c)*qDef - share;                % gain a tricher

figure;
bar([Pcart Pconc c], 'FaceColor', [0.30 0.50 0.72]);
set(gca, 'XTickLabel', {'Prix cartel', 'Prix concurrence', 'Cout'});
ylabel('Prix'); grid on;
title(sprintf('Cartel a %d membres : gain a tricher = %.0f par membre', N, gain));

Change et parité de pouvoir d'achat

Une monnaie est-elle « chère » ou « bon marché » ? La parité de pouvoir d'achat (PPA) part d'une idée simple : à long terme, un même panier de biens devrait coûter la même chose partout, une fois converti. C'est la logique de l'indice Big Mac. En comparant le taux PPA au taux réel du marché, on voit si une monnaie est surévaluée (le panier est moins cher ailleurs) ou sous-évaluée. Déplacez les prix et le taux de change.

Voir le code MATLAB
% Parite de pouvoir d'achat (logique Big Mac)
pdom = 5; pfor = 6; e = 1.10;          % prix ici (EUR), prix ailleurs (USD), taux marche $/EUR
eppa = pfor / pdom;                    % taux PPA qui egalise le panier
misval = e/eppa - 1;                   % > 0 : euro surevalue (panier moins cher ailleurs)

figure;
bar([e eppa], 'FaceColor', [0.30 0.50 0.72]);
set(gca, 'XTickLabel', {'Taux marche', 'Taux PPA'});
ylabel('USD par EUR'); grid on;
if misval > 0
  verdict = sprintf('euro surevalue de %.0f%%', misval*100);
else
  verdict = sprintf('euro sous-evalue de %.0f%%', -misval*100);
end
title(['Parite de pouvoir d''achat : ' verdict]);

Heckscher-Ohlin : commerce et dotations

Pourquoi un pays exporte-t-il certains biens plutôt que d'autres ? Parce qu'il est abondant dans le facteur qu'ils utilisent. Un pays riche en capital produit à bas coût le bien intensif en capital : sa frontière de production penche de ce côté. Au prix mondial, il s'y spécialise, l'exporte, importe l'autre bien, et se retrouve à consommer AU-DELÀ de sa frontière : c'est le gain à l'échange. Déplacez l'abondance en capital et le prix mondial.

Voir le code MATLAB
% Heckscher-Ohlin : frontiere de production (ellipse) + prix mondial
Ym = 100; Xm = 120; Pw = 1.2;          % capacites (X intensif capital), prix mondial de X
th = atan(Ym/(Pw*Xm));                 % specialisation au prix mondial
Xp = Xm*cos(th);  Yp = Ym*sin(th);     % point de production
V  = Pw*Xp + Yp;                       % valeur produite (au prix mondial)

t = linspace(0, pi/2, 100);
figure; hold on;
plot(Xm*cos(t), Ym*sin(t), 'LineWidth', 2);              % frontiere de production
plot([0 V/Pw], [V 0], '--');                             % droite de prix mondial (Pw*X + Y = V)
plot(Xp, Yp, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.20 0.45 0.70]);          % production
plot(V/(2*Pw), V/2, 'p', 'MarkerSize', 14, 'MarkerFaceColor', [0.80 0.20 0.15]);  % conso 50/50 (au-dela)
xlabel('Bien X (intensif capital)'); ylabel('Bien Y');
legend('Frontiere de production', 'Prix mondial', 'Production', 'Consommation', 'Location', 'northeast');
title('Heckscher-Ohlin : on consomme au-dela de la frontiere');
grid on;

La courbe en J

Que se passe-t-il quand une monnaie se déprécie ? À court terme, les importations coûtent déjà plus cher mais les volumes n'ont pas eu le temps de s'ajuster : la balance commerciale se DÉGRADE d'abord. Puis les exportations deviennent plus compétitives, les importations reculent, et la balance s'améliore, à condition que les élasticités soient assez fortes (condition de Marshall-Lerner). D'où la trajectoire en forme de J. Réglez l'ampleur de la dévaluation, les élasticités et la vitesse d'ajustement.

Voir le code MATLAB
% Courbe en J : balance commerciale apres une devaluation
d = 0.15;              % ampleur de la devaluation (15%)
eX = 0.7; eM = 0.6;    % elasticites export / import
tau = 6;               % constante de temps d'ajustement (mois)
t = 0:0.2:24;
TB = -d + d*(eX+eM)*(1 - exp(-t/tau));   % creux immediat puis redressement
ml = eX + eM;          % Marshall-Lerner : amelioration durable si > 1

figure; hold on;
plot(t, TB*100, 'LineWidth', 2);
plot([0 24], [0 0], 'k--');
xlabel('Mois apres la devaluation'); ylabel('Balance commerciale (points)');
title(sprintf('Courbe en J (Marshall-Lerner : eX+eM = %.1f)', ml));
grid on;

Heckscher-Ohlin : deux pays qui échangent

Deux pays, deux biens : des machines (intensives en capital) et du textile (intensif en travail). Le Nord est abondant en capital, le Sud en travail. Chacun a donc, en autarcie, un prix relatif différent : les machines sont bon marché au Nord, le textile bon marché au Sud. Ouvrez le commerce : un prix mondial unique s'établit ENTRE les deux prix d'autarcie, chaque pays se spécialise dans le bien qui utilise son facteur abondant, et les DEUX consomment au-delà de leur frontière de production. Réglez les dotations et la taille du Sud.

Voir le code MATLAB
% Heckscher-Ohlin a deux pays : prix mondial entre les deux autarcies
Nm = 120; Nt = 80;     % Nord (abondant en capital) : max machines / textile
Sm = 60;  St = 110;    % Sud (abondant en travail)
pN = Nt/Nm;            % prix d'autarcie des machines au Nord (bas)
pS = St/Sm;            % prix d'autarcie au Sud (haut)
pW = sqrt(pN*pS);      % prix mondial (entre les deux)

figure; hold on;
plot([0 Nm],[Nt 0], 'LineWidth', 2);      % frontiere du Nord
plot([0 Sm],[St 0], 'LineWidth', 2);      % frontiere du Sud
xlabel('Machines'); ylabel('Textile');
legend(sprintf('Nord (prix auto = %.2f)', pN), sprintf('Sud (prix auto = %.2f)', pS), 'Location', 'northeast');
title(sprintf('Prix mondial = %.2f : chacun se specialise et consomme au-dela', pW));
grid on;

Sanctions et interdépendance armée

Quand deux économies dépendent l'une de l'autre, l'une peut transformer ce lien en arme : couper un approvisionnement critique pour contraindre l'autre. Mais une sanction coûte aussi à celui qui l'impose, et son efficacité s'érode : avec le temps, la cible trouve d'autres fournisseurs et débouchés. On suit ici la douleur infligée à la cible mois après mois, comparée au coût que le pays sanctionneur subit lui-même. Réglez la dépendance de la cible, sa capacité de contournement et l'exposition du sanctionneur.

Voir le code MATLAB
% Sanctions : douleur infligee a la cible vs cout du sanctionneur
depTarget = 0.6;       % dependance de la cible
evasion   = 0.08;      % capacite de contournement (par mois)
expo      = 0.25;      % exposition du sanctionneur
t = 0:1:24;
pain = depTarget * exp(-evasion*t) * 100;   % la cible contourne avec le temps
cost = expo * 50 * ones(size(t));           % cout du sanctionneur (stable)

figure; hold on;
plot(t, pain, 'LineWidth', 2);
plot(t, cost, 'LineWidth', 2);
xlabel('Mois'); ylabel('Cout economique (indice)');
legend('Douleur infligee a la cible', 'Cout pour le sanctionneur');
title('Sanction : forte au debut, elle s erode quand la cible contourne');
grid on;

La malédiction des ressources

Pourquoi des pays débordant de pétrole ou de minerais croissent-ils souvent MOINS vite que des pays qui en manquent ? Rente qui nourrit la corruption, monnaie qui s'apprécie et étouffe l'industrie (maladie hollandaise), prix volatils : c'est la malédiction des ressources. Mais tout se joue sur les institutions. Sous un certain seuil de qualité institutionnelle, plus le pays dépend de ses ressources, moins il croît ; au-dessus, la manne devient un atout (Norvège contre d'autres). Réglez la qualité des institutions, l'intensité de la maladie hollandaise et la dépendance aux ressources.

Voir le code MATLAB
% Malediction des ressources : croissance vs dependance, selon les institutions
dep = 0:0.02:1;                        % dependance aux ressources
instBad = 0.3; instGood = 0.8;         % qualite des institutions
g = @(inst) 2 + (inst-0.5)*8.*dep - 3*(1-inst)*dep.^2;   % croissance (illustratif)

figure; hold on;
plot(dep*100, g(instBad), 'LineWidth', 2);
plot(dep*100, g(instGood), 'LineWidth', 2);
plot([0 100],[0 0],'k--');
xlabel('Dependance aux ressources (%)'); ylabel('Croissance (%)');
legend('Institutions faibles', 'Institutions solides', 'Location', 'southwest');
title('Ressources : malediction si institutions faibles, atout si solides');
grid on;

Délocaliser ou relocaliser ?

Faut-il produire loin, là où la main-d'œuvre est bon marché, ou près de chez soi ? Délocaliser baisse les salaires mais alourdit le transport, les droits de douane et le RISQUE de rupture (pandémie, guerre, blocage d'un détroit). On calcule le coût total d'une unité selon la part délocalisée, et on cherche la part qui le minimise. Quand la prime de risque monte, l'optimum se déplace vers la relocalisation. Réglez l'écart de salaire, les coûts logistiques et douaniers, et la prime de résilience.

Voir le code MATLAB
% Delocaliser ou relocaliser : cout total selon la part delocalisee
f = 0:0.01:1;                 % part delocalisee
wgap = 0.30;                  % economie de salaire a l'etranger
logi = 0.10;                  % surcout logistique + douane
risk = 0.25;                  % prime de risque de rupture (croit avec f)
cost = 1 - wgap*f + logi*f + risk*f.^2;
[cmin, i] = min(cost);

figure; hold on;
plot(f*100, cost, 'LineWidth', 2);
plot(f(i)*100, cmin, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Part delocalisee (%)'); ylabel('Cout unitaire (indice)');
title(sprintf('Optimum : delocaliser %.0f%% (la prime de risque limite)', f(i)*100));
grid on;

Le triangle des incompatibilités

Un pays ne peut pas tout avoir en même temps. Entre trois objectifs (un taux de change fixe, la libre circulation des capitaux et une politique monétaire autonome), il ne peut en tenir que DEUX : c'est le trilemme de Mundell. Choisissez le régime que vous privilégiez : le triangle éclaire le côté que vous gardez, grise l'objectif sacrifié, et donne l'exemple réel correspondant (zone euro, Chine, États-Unis...).

Voir le code MATLAB
% Trilemme de Mundell : on ne peut tenir que 2 des 3 objectifs
figure; hold on;
V = [0 0; 1 0; 0.5 0.87];              % 3 sommets du triangle
patch(V(:,1), V(:,2), [0.90 0.86 0.75], 'EdgeColor', [0.2 0.2 0.2], 'LineWidth', 1.5);
noms = {'Change fixe', 'Capitaux libres', 'Politique monetaire autonome'};
dy = [-0.07 -0.07 0.06];
for k = 1:3
  text(V(k,1), V(k,2)+dy(k), noms{k}, 'HorizontalAlignment', 'center', 'FontWeight', 'bold');
end
plot([V(1,1) V(2,1)], [V(1,2) V(2,2)], 'LineWidth', 3, 'Color', [0.80 0.20 0.15]);
axis equal off;
title('Choisir un cote (2 objectifs) revient a sacrifier le sommet oppose');

Union douanière : création ou détournement ?

Former un bloc commercial (UE, USMCA) enrichit-il toujours ? Pas forcément. En supprimant les droits de douane avec un partenaire, on peut remplacer une production nationale coûteuse par des imports moins chers (CRÉATION de commerce, un gain) ; mais on peut aussi détourner ses achats du fournisseur mondial le plus efficace vers le partenaire, juste parce qu'il échappe au tarif (DÉTOURNEMENT de commerce, une perte, avec en prime les recettes douanières perdues). Réglez le prix mondial, le prix du partenaire et le tarif : le bilan net bascule.

Voir le code MATLAB
% Union douaniere : creation vs detournement de commerce
Pw = 100; Ppart = 108; tar = 0.20;     % prix mondial, prix du partenaire, tarif externe
Pbefore = Pw*(1+tar);                  % avant : import mondial + tarif
Pafter  = min(Ppart, Pbefore);         % apres : import du partenaire, sans tarif
creation = max(0, Pbefore - Pafter);           % baisse de prix pour le consommateur
detourn  = (Ppart > Pw) * (Ppart - Pw);        % surcout vs le vrai moins-disant mondial

figure;
bar([Pw Pbefore Ppart Pafter], 'FaceColor', [0.30 0.50 0.72]);
set(gca, 'XTickLabel', {'Mondial', 'Avant (tarif)', 'Partenaire', 'Apres union'});
ylabel('Prix paye'); grid on;
title(sprintf('Creation -%.0f pour le conso, mais detournement +%.0f vs mondial', creation, detourn));

Le modèle de gravité du commerce

Avec qui un pays commerce-t-il le plus ? Comme la gravité de Newton : proportionnellement au PRODUIT des deux économies, et à l'inverse de la DISTANCE qui les sépare. Un gros voisin proche pèse bien plus qu'une petite économie lointaine. On trace le flux de commerce selon la distance ; réglez la taille des deux pays et la sensibilité à la distance, et placez un partenaire pour lire le flux attendu.

Voir le code MATLAB
% Modele de gravite : le commerce vs la distance et la taille
Gi = 1000; Gj = 800;      % PIB des deux pays
G0 = 1; k = 1;            % constante, elasticite a la distance
dist = linspace(200, 8000, 200);
trade = G0 * (Gi*Gj) ./ dist.^k;

figure;
plot(dist, trade, 'LineWidth', 2);
xlabel('Distance (km)'); ylabel('Commerce bilateral (indice)');
title('Gravite : le commerce croit avec la taille, decroit avec la distance');
grid on;

Microéconomie

Comment se forment les prix et les quantités sur un marché.

Offre & demande : l'équilibre du marché

Sur un marché, le prix s'ajuste là où la quantité que les acheteurs veulent (la demande, qui baisse avec le prix) égale celle que les vendeurs offrent (l'offre, qui monte avec le prix) : c'est l'équilibre. En ajoutant une taxe par unité, un coin se creuse entre le prix payé et le prix reçu : les échanges diminuent, l'État récolte une recette (rectangle vert), et une partie de la valeur disparaît, la perte sèche (triangle orange).

Voir le code MATLAB
% Equilibre offre-demande et effet d'une taxe par unite
A = 100; B = 1;   % demande : P = A - B*Q
C = 20;  D = 1;   % offre   : P = C + D*Q
t = 20;           % taxe par unite
Qs = (A - C)/(B + D);              % quantite d'equilibre (sans taxe)
Qt = (A - C - t)/(B + D);          % quantite avec taxe
Pc = A - B*Qt;                     % prix paye par le consommateur
Pp = Pc - t;                       % prix recu par le producteur
Peq = A - B*Qs;                    % prix d'equilibre sans taxe
recette = t*Qt;  perte = 0.5*t*(Qs - Qt);

Q = linspace(0, A, 200);
figure; hold on;
plot(Q, A - B*Q, 'LineWidth', 2);            % demande
plot(Q, C + D*Q, 'LineWidth', 2);            % offre
fill([0 Qt Qt 0], [Pp Pp Pc Pc], [0.30 0.55 0.35], 'FaceAlpha', 0.35, 'EdgeColor', 'none');  % recette
fill([Qt Qt Qs], [Pc Pp Peq], [0.85 0.55 0.20], 'FaceAlpha', 0.45, 'EdgeColor', 'none');     % perte seche
xlabel('Quantite'); ylabel('Prix'); xlim([0 A]); ylim([0 A]);
legend('Demande', 'Offre', 'Recette fiscale', 'Perte seche', 'Location', 'northeast');
title(sprintf('Taxe de %g : recette = %.0f, perte seche = %.0f', t, recette, perte));
grid on;

Le monopole

Sur un marché concurrentiel, le prix s'aligne sur le coût de production. Un vendeur unique, lui, choisit la quantité qui maximise son profit : là où sa recette marginale égale son coût marginal. Résultat, il vend moins cher pour le client ? Non : il vend plus cher et en moindre quantité. Une partie des échanges utiles n'a jamais lieu : c'est la perte sèche. Déplacez le coût marginal et la demande pour comparer monopole et concurrence.

Voir le code MATLAB
% Monopole vs concurrence
A = 100; b = 1; c = 20;      % demande P = A - b*Q, cout marginal c
Qm = (A-c)/(2*b);   Pm = (A+c)/2;    % monopole : recette marginale = cout marginal
Qc = (A-c)/b;                        % concurrence : prix = cout marginal
dwl = 0.5*(Qc-Qm)*(Pm-c);            % perte seche
profit = (Pm-c)*Qm;                  % profit du monopole

Q = linspace(0, A, 200);
figure; hold on;
plot(Q, A - b*Q, 'LineWidth', 2);            % demande
plot(Q, A - 2*b*Q, '--');                    % recette marginale
plot([0 A], [c c], 'LineWidth', 1.5);        % cout marginal
plot(Qm, Pm, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.20 0.45 0.70]);   % monopole
plot(Qc, c, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.30 0.60 0.35]);    % concurrence
xlabel('Quantite'); ylabel('Prix'); xlim([0 A]); ylim([0 A]);
legend('Demande', 'Recette marginale', 'Cout marginal', 'Monopole', 'Concurrence', 'Location', 'northeast');
title(sprintf('Monopole Q=%.0f a P=%.0f (concurrence Q=%.0f) ; perte seche %.0f', Qm, Pm, Qc, dwl));
grid on;

Cournot : le duopole

Entre le monopole (un seul vendeur) et la concurrence (une multitude), le cas le plus courant est celui de quelques géants face à face : Boeing et Airbus, les fondeurs de puces, les opérateurs télécoms. Dans le modèle de Cournot, chaque firme choisit sa quantité en anticipant celle de sa rivale. La meilleure réponse de l'une dépend de la production de l'autre : ces deux « courbes de réaction » se croisent en un point d'équilibre stable (Nash), où aucune n'a intérêt à bouger seule. Déplacez les coûts : la firme la plus efficace produit davantage et capte le marché ; si une rivale décroche, on glisse vers le monopole.

Voir le code MATLAB
% Duopole de Cournot : deux firmes choisissent leur quantite
a = 120; b = 1;        % demande inverse : P = a - b*(q1 + q2)
c1 = 20; c2 = 40;      % couts marginaux des deux firmes
% Equilibre de Nash-Cournot (solution interieure, sinon une firme sort)
q1 = max(0, (a - 2*c1 + c2)/(3*b));
q2 = max(0, (a - 2*c2 + c1)/(3*b));
P   = a - b*(q1 + q2);
pi1 = (P - c1)*q1;  pi2 = (P - c2)*q2;

% Courbes de reaction : meilleure reponse a la quantite de l'autre
q = linspace(0, (a - min(c1,c2))/b, 200);
BR1 = max(0, (a - c1 - b*q)/(2*b));    % reponse de la firme 1 a q2 = q
BR2 = max(0, (a - c2 - b*q)/(2*b));    % reponse de la firme 2 a q1 = q

figure; hold on;
plot(BR1, q, 'LineWidth', 2);          % firme 1 (axe x = q1)
plot(q, BR2, 'LineWidth', 2);          % firme 2
plot(q1, q2, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.17 0.17 0.14]);  % Nash
xlabel('Quantite firme 1'); ylabel('Quantite firme 2');
legend('Reaction firme 1', 'Reaction firme 2', 'Equilibre de Nash');
title(sprintf('Cournot : q1=%.1f, q2=%.1f, P=%.1f, profit total=%.0f', q1, q2, P, pi1+pi2));
grid on;

Bertrand : la concurrence par les prix

Cournot fait choisir les quantités ; Bertrand fait choisir les prix. Le changement paraît anodin, mais le résultat est spectaculaire. Deux firmes vendant un produit proche se livrent une guerre des prix : chacune est tentée de baisser un peu sous le rival pour capter le marché. À l'équilibre, le prix tombe presque au coût de production, même avec seulement deux vendeurs : c'est le paradoxe de Bertrand. Ici les produits sont différenciés (marques, qualité), ce qui laisse un peu de marge. Déplacez la substituabilité : plus les produits se ressemblent, plus le prix chute vers le coût, et les courbes de réaction (cette fois en prix) se croisent plus bas.

Voir le code MATLAB
% Bertrand differencie : deux firmes fixent leur PRIX
a = 60; c = 20; d = 1.5;        % taille du marche, cout marginal, substituabilite
% demande q_i = a - (1+d)*p_i + d*p_j ; equilibre symetrique de Nash :
p = (a + (1+d)*c)/(2+d);        % prix d'equilibre
q = a - p;                      % quantite par firme
profit = (p - c)*q;

% courbes de reaction (en prix) : p_i = [a + (1+d)*c + d*p_j] / (2*(1+d))
A = (a + (1+d)*c)/(2*(1+d)); s = d/(2*(1+d));
pj = linspace(0, a, 200);
BR1 = A + s*pj;                 % reponse de la firme 1 a p2 = pj
BR2 = A + s*pj;                 % reponse de la firme 2 a p1 = pj (symetrique)

figure; hold on;
plot(BR1, pj, 'LineWidth', 2);          % firme 1 (axe x = p1)
plot(pj, BR2, 'LineWidth', 2);          % firme 2
plot(p, p, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.17 0.17 0.14]);  % Nash
plot([c a], [c a], ':');                 % reference : prix = cout
xlabel('Prix firme 1'); ylabel('Prix firme 2');
legend('Reaction firme 1', 'Reaction firme 2', 'Nash', 'Prix = cout', 'Location', 'southeast');
title(sprintf('Bertrand : prix %.1f (cout %.0f), marge %.1f', p, c, p-c));
grid on;

Les effets de réseau

Certains produits ne valent que par le nombre de leurs utilisateurs : un téléphone, une messagerie, une place de marché, un standard technique. Plus il y a de monde, plus rejoindre devient intéressant, et l'adoption s'auto-renforce. La courbe montre, pour chaque part d'utilisateurs anticipée, la part qui adopte réellement. Là où elle croise la diagonale, les anticipations se réalisent : ce sont les équilibres. Entre les deux se cache un point de bascule : en dessous, le marché s'effondre vers zéro ; au-dessus, il s'emballe vers la domination (le « winner-take-all »). Déplacez la force du réseau et le prix : voyez pourquoi les plateformes cassent leurs prix au lancement pour franchir ce seuil.

Voir le code MATLAB
% Effets de reseau : adoption avec anticipations (bascule / tipping)
s = 2; b = 12; p = 8; k = 0.8;   % valeur seule, force du reseau, prix, sensibilite
xe = linspace(0, 1, 400);        % part d'adoption ANTICIPEE
xa = 1 ./ (1 + exp(-k*(s + b*xe - p)));   % part EFFECTIVE (meilleure reponse)

figure; hold on;
plot(xe, xa, 'LineWidth', 2);            % courbe d'adoption effective
plot([0 1], [0 1], '--');                % diagonale : attendue = effective
% equilibres = points fixes ou xa(xe) = xe (changements de signe de xa - xe)
g = xa - xe;
idx = find(g(1:end-1).*g(2:end) < 0);
xeq = xe(idx) - g(idx).*(xe(idx+1)-xe(idx))./(g(idx+1)-g(idx));
plot(xeq, xeq, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.17 0.17 0.14]);
xlabel('Part anticipee'); ylabel('Part effective');
legend('Adoption effective', 'Attendue = effective', 'Equilibres', 'Location', 'southeast');
title('Effets de reseau : point de bascule et equilibres multiples');
axis([0 1 0 1]); grid on;

Enchères : la malédiction du vainqueur

Un lot de valeur incertaine (une licence 5G, un bloc pétrolier, un marché public) est mis aux enchères. Chacun s'en fait une estimation, forcément imparfaite. Problème : celui qui remporte l'enchère est souvent celui qui a le plus surestimé le lot. Gagner est donc une mauvaise nouvelle sur sa vraie valeur, et le vainqueur tend à trop payer : c'est la malédiction du vainqueur. Et plus il y a d'enchérisseurs, plus l'écart se creuse. Déplacez le nombre de concurrents et l'incertitude : voyez de combien il faut baisser son enchère sous son estimation pour ne pas se faire piéger.

Voir le code MATLAB
% Malediction du vainqueur : enchere a valeur commune incertaine
V = 50; w = 20;                 % valeur reelle du lot, incertitude (+/- sur l'estimation)
N = 2:24;                       % nombre d'encherisseurs
curse = w*(N-1)./(N+1);         % sur-estimation moyenne du gagnant (max de N bruits)
paye  = V + curse;              % prix paye si chacun enchérit son estimation

figure; hold on;
plot(N, paye, 'LineWidth', 2);            % paiement du gagnant naif
plot([N(1) N(end)], [V V], '--');         % valeur reelle
fill([N fliplr(N)], [paye V*ones(size(N))], [0.71 0.15 0.12], 'FaceAlpha', 0.16, 'EdgeColor', 'none');  % malediction
xlabel('Nombre d''encherisseurs'); ylabel('Montant');
legend('Paiement du gagnant naif', 'Valeur reelle', 'Malediction', 'Location', 'southeast');
title('Malediction du vainqueur : le sur-paiement grandit avec la concurrence');
grid on;

Plafond et plancher de prix

Bloquer un prix par la loi semble protecteur, mais déplace le marché hors de son équilibre. Un plafond sous l'équilibre (contrôle des loyers) fait apparaître une pénurie : les acheteurs en veulent plus qu'il n'y en a d'offert. Un plancher au-dessus (salaire minimum, prix agricole garanti) crée un surplus invendu. Déplacez le prix imposé : selon qu'il tombe sous ou au-dessus de l'équilibre, la simulation bascule entre pénurie et surplus.

Voir le code MATLAB
% Plafond / plancher de prix
A = 100; s = 1; P0 = 30;     % demande Qd=A-P, offre Qs=s*P, prix impose P0
Peq = A/(1+s);   Qeq = A*s/(1+s);    % equilibre libre
Qd = A - P0;   Qs = s*P0;
echange = min(Qd, Qs);               % cote court du marche
ecart = abs(Qd - Qs);                % penurie si P0 sous l'equilibre, sinon surplus

P = linspace(0, A, 200);
figure; hold on;
plot(A - P, P, 'LineWidth', 2);              % demande (Q en abscisse)
plot(s*P,  P, 'LineWidth', 2);               % offre
plot([0 A], [P0 P0], 'k--');                 % prix impose
plot(Qd, P0, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.20 0.45 0.70]);
plot(Qs, P0, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Quantite'); ylabel('Prix'); xlim([0 A]); ylim([0 A]);
legend('Demande', 'Offre', 'Prix impose', 'Demande a P0', 'Offre a P0', 'Location', 'northeast');
if P0 < Peq, etat = 'penurie'; else etat = 'surplus'; end
title(sprintf('Prix impose %g (equilibre %.0f) : %s de %.0f', P0, Peq, etat, ecart));
grid on;

Externalité et taxe pigouvienne

Une usine qui pollue impose un coût aux autres (santé, climat) qu'elle ne paie pas : son coût privé est plus bas que le coût réel pour la société. Résultat, le marché produit trop. Une taxe par unité, calibrée sur le dommage causé (la taxe de Pigou), fait payer ce coût au pollueur et ramène la production au niveau socialement optimal. Déplacez le coût externe et la taxe : quand la taxe égale le dommage, la perte pour la société disparaît.

Voir le code MATLAB
% Externalite et taxe pigouvienne
A = 100; c0 = 10; s = 1;     % demande P=A-Q, cout prive MPC = c0 + s*Q
x = 20; t = 0;               % cout externe (dommage) et taxe par unite
Qm   = (A - c0 - t)/(1+s);   % quantite de marche (avec taxe)
Qopt = (A - c0 - x)/(1+s);   % optimum social (cout social = MPC + x)
dwl = 0.5*abs(Qm-Qopt)*abs(x-t);     % perte pour la societe (nulle si t = x)

Q = linspace(0, A - c0, 200);
figure; hold on;
plot(Q, A - Q, 'LineWidth', 2);              % demande
plot(Q, c0 + s*Q, 'LineWidth', 2);           % cout prive (MPC)
plot(Q, c0 + x + s*Q, '--');                 % cout social (MPC + dommage)
plot(Q, c0 + t + s*Q, ':');                  % cout prive + taxe
plot(Qm, A-Qm, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);      % marche
plot(Qopt, A-Qopt, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.30 0.60 0.35]);  % optimum
xlabel('Quantite'); ylabel('Prix'); ylim([0 A]);
legend('Demande', 'Cout prive', 'Cout social', 'Cout prive + taxe', 'Marche', 'Optimum', 'Location', 'northeast');
title(sprintf('Marche Q=%.0f vs optimum Q=%.0f ; perte %.0f (nulle si taxe = dommage)', Qm, Qopt, dwl));
grid on;

Le choix du consommateur

Avec un budget donné, comment répartir sa dépense entre deux biens ? Les courbes d'indifférence relient tous les paniers qui procurent la même satisfaction ; la droite de budget montre ce que l'on peut s'offrir. Le meilleur choix se trouve au point de tangence : là où l'on atteint la courbe d'indifférence la plus haute possible. Déplacez les prix, le revenu et vos préférences, et regardez le panier optimal se déplacer.

Voir le code MATLAB
% Choix du consommateur : utilite Cobb-Douglas U = x^a * y^(1-a)
px = 2; py = 2; R = 60; a = 0.5;       % prix, budget, preference pour X
xStar = a*R/px;   yStar = (1-a)*R/py;  % panier optimal (tangence)
Uopt  = xStar^a * yStar^(1-a);         % satisfaction atteinte
% A l'optimum : TMS = px/py (le rapport des prix egalise l'arbitrage voulu)

x = linspace(0.1, R/px, 200);
yBudget = (R - px*x)/py;               % droite de budget
yIndiff = (Uopt ./ x.^a).^(1/(1-a));   % courbe d'indifference U = Uopt
figure; hold on;
plot(x, yBudget, 'LineWidth', 2);
plot(x, yIndiff, 'LineWidth', 2);
plot(xStar, yStar, 'o', 'MarkerSize', 9, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Bien X'); ylabel('Bien Y'); ylim([0 R/py]);
legend('Budget', 'Courbe d''indifference', 'Panier optimal', 'Location', 'northeast');
title('Optimum : la courbe d''indifference est tangente au budget');
grid on;

Les coûts de l'entreprise

À quel prix une entreprise a-t-elle intérêt à produire, et combien ? Le coût marginal (Cm) est celui de la dernière unité ; le coût moyen (CM) a une forme en U. L'entreprise produit là où le prix égale le coût marginal. Au-dessus du seuil de rentabilité (le minimum du coût moyen), elle fait un profit ; en dessous du point de fermeture (le minimum du coût variable moyen), elle s'arrête. Déplacez les coûts et le prix de marché.

Voir le code MATLAB
% Couts de l'entreprise : C(q) = F + c*q + d*q^2
F = 100; c = 6; d = 1; P = 30;         % cout fixe, cout marginal de base, courbure, prix
qBe = sqrt(F/d);  pBe = F/qBe + c + d*qBe;   % seuil de rentabilite (min du CM)
qStar = max(0,(P-c)/(2*d));            % offre : P = Cm
profit = P*qStar - (F + c*qStar + d*qStar^2);

q = linspace(0.5, 20, 200);
figure; hold on;
plot(q, c + 2*d*q, 'LineWidth', 2);          % cout marginal
plot(q, F./q + c + d*q, 'LineWidth', 2);     % cout moyen (en U)
plot(q, c + d*q, '--');                      % cout variable moyen
plot([0 20], [P P], 'k:');                   % prix de marche
plot(qStar, P, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Quantite produite'); ylabel('Cout / prix'); ylim([0 60]);
legend('Cout marginal', 'Cout moyen', 'Cout variable moyen', 'Prix', 'Production optimale', 'Location', 'northeast');
title(sprintf('Seuil de rentabilite q=%.1f ; a P=%g on produit q=%.1f', qBe, P, qStar));
grid on;

L'élasticité-prix de la demande

De combien la quantité demandée baisse-t-elle quand le prix monte ? C'est l'élasticité. Quand la demande est élastique (les clients réagissent fort), baisser le prix augmente la recette totale ; quand elle est inélastique, c'est l'inverse. Le rectangle vert représente la recette (prix × quantité). Déplacez le prix et voyez la recette gonfler ou se dégonfler.

Voir le code MATLAB
% Elasticite-prix : demande lineaire Q = A - b*P
A = 100; b = 2; P = 18;                % taille du marche, sensibilite, prix
Q = max(0, A - b*P);                   % quantite demandee
elas = b*P / (A - b*P);                % |elasticite| au point P
TR = P*Q;                              % recette totale (maximale a l'elasticite unitaire)

Pv = linspace(0, A/b, 200);
figure; hold on;
plot(A - b*Pv, Pv, 'LineWidth', 2);          % demande (Q en abscisse)
fill([0 Q Q 0], [0 0 P P], [0.30 0.55 0.35], 'FaceAlpha', 0.35, 'EdgeColor', 'none');  % recette P*Q
plot([0 A], [A/(2*b) A/(2*b)], 'k:');        % elasticite unitaire (recette max)
xlabel('Quantite'); ylabel('Prix'); xlim([0 A]); ylim([0 A/b]);
legend('Demande', 'Recette (P x Q)', 'Elasticite unitaire', 'Location', 'northeast');
title(sprintf('A P=%g : |elasticite| = %.2f, recette = %.0f', P, elas, TR));
grid on;

Le marché du travail

Le travail s'échange comme un bien : les entreprises en demandent d'autant moins que le salaire est élevé, les personnes en offrent d'autant plus. Le salaire d'équilibre égalise les deux. Fixez un salaire minimum au-dessus de cet équilibre et le chômage apparaît : plus de gens veulent travailler qu'il n'y a d'emplois. Un arbitrage réel des politiques de l'emploi. Déplacez l'activité, la population active et le salaire minimum.

Voir le code MATLAB
% Marche du travail : demande LD = a - beta*w, offre LS = g*w
a = 100; beta = 2; g = 2; wMin = 40;   % activite, sensibilites, salaire minimum
wStar = a/(beta+g);   Lstar = g*wStar; % salaire et emploi d'equilibre

w = linspace(0, a/beta, 200);
figure; hold on;
plot(a - beta*w, w, 'LineWidth', 2);   % demande de travail (L en abscisse)
plot(g*w, w, 'LineWidth', 2);          % offre de travail
plot([0 a], [wMin wMin], 'k--');       % salaire minimum
if wMin > wStar                        % le salaire minimum "mord"
  emploi  = a - beta*wMin;             % cote demande (le plus court)
  offre   = g*wMin;
  chomage = offre - emploi;            % offre excedentaire
  plot([emploi offre], [wMin wMin], 'LineWidth', 3, 'Color', [0.80 0.20 0.15]);   % chomage
  ttl = sprintf('Salaire min %g au-dessus de %.0f : chomage = %.0f', wMin, wStar, chomage);
else
  ttl = sprintf('Salaire min %g sous l equilibre %.0f : sans effet', wMin, wStar);
end
xlabel('Quantite de travail'); ylabel('Salaire'); xlim([0 a]);
legend('Demande de travail', 'Offre de travail', 'Salaire minimum', 'Location', 'northeast');
title(ttl); grid on;

La tragédie des communs

Une ressource partagée sans règle (une zone de pêche, un pâturage, le climat, une nappe d'eau) finit surexploitée. Chacun a intérêt à en prendre un peu plus pour lui, mais impose un coût à tous les autres. Résultat : l'effort collectif dépasse l'optimum et de la valeur est détruite. Plus les usagers sont nombreux et non coordonnés, pire c'est ; un seul propriétaire, ou une règle commune, atteint l'optimum. Déplacez le nombre d'usagers, la richesse de la ressource et le coût.

Voir le code MATLAB
% Tragedie des communs : valeur sociale V(E) = E*(A - c - E)
A = 100; c = 20; N = 6;                % richesse, cout de l'effort, nombre d'usagers
Eopt = (A - c)/2;                      % optimum (usager unique / regle commune)
En   = N*(A - c)/(N + 1);              % effort a N usagers non coordonnes (-> A-c si N grand)
V = @(E) E.*(A - c - E);
perte = V(Eopt) - V(En);               % valeur detruite par la surexploitation

E = linspace(0, A - c, 200);
figure; hold on;
plot(E, V(E), 'LineWidth', 2);
plot(Eopt, V(Eopt), 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.30 0.60 0.35]);   % optimum
plot(En,   V(En),   'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);   % N usagers
xlabel('Effort total'); ylabel('Valeur creee');
legend('Valeur V(E)', 'Optimum', 'A N usagers', 'Location', 'south');
title(sprintf('%d usagers surexploitent : valeur detruite = %.0f', N, perte));
grid on;

Le marché des « lemons »

Pourquoi le marché des voitures d'occasion peut-il s'effondrer alors que tout le monde y gagnerait à échanger ? Parce que le vendeur connaît la qualité de sa voiture, pas l'acheteur. À un prix donné, seuls les propriétaires des moins bonnes voitures acceptent de vendre : la qualité moyenne offerte chute, l'acheteur baisse son prix, de moins bonnes voitures encore restent... jusqu'à ne plus vendre que des « lemons » (des tacots). Réglez le gain à l'échange et le niveau d'information (garanties, certification) pour voir le marché survivre ou s'effondrer.

Voir le code MATLAB
% Marche des lemons (Akerlof) : la qualite est cachee a l'acheteur
qmax = 100; gamma = 1.4;               % qualite max ; l'acheteur valorise gamma * qualite
p = linspace(0, qmax, 200);
avgOffered = min(p, qmax)/2;           % qualite moyenne offerte a prix p (vendeurs de valeur <= p)
buyerMax   = gamma * avgOffered;       % prix max que l'acheteur accepte

figure; hold on;
plot(p, avgOffered, 'LineWidth', 2);
plot(p, buyerMax, 'LineWidth', 2);
plot(p, p, 'k--');                     % droite a 45 degres
xlabel('Prix'); ylabel('Qualite moyenne / valeur');
legend('Qualite moyenne offerte', 'Valeur pour l''acheteur', '45 degres', 'Location', 'northwest');
if gamma < 2
  verdict = 'le marche se contracte (seuls les tacots restent)';
else
  verdict = 'le marche tient';
end
title(['Lemons : ' verdict]);
grid on;

L'aléa moral

Une fois bien assuré contre un risque, on fait... moins attention. C'est l'aléa moral : la couverture réduit l'incitation à se protéger. On suit l'effort de prévention et la probabilité d'accident selon le taux de couverture : plus l'assurance paie, moins l'assuré prend soin, et plus les accidents deviennent fréquents. D'où les franchises et les tickets modérateurs. Réglez la couverture, le coût de la prévention et la taille de la perte.

Voir le code MATLAB
% Alea moral : couverture d'assurance vs effort de prevention
cov = linspace(0, 1, 200);             % taux de couverture
k = 1.5;                               % sensibilite de l'effort a la couverture
effort = max(0, 1 - k*cov);            % on se protege moins quand on est couvert
pAcc   = 0.05 + 0.35*(1 - effort);     % probabilite d'accident (monte si effort baisse)

figure; hold on;
plot(cov*100, effort*100, 'LineWidth', 2);
plot(cov*100, pAcc*100, 'LineWidth', 2);
xlabel('Taux de couverture (%)'); ylabel('Niveau (%)');
legend('Effort de prevention', 'Probabilite d''accident', 'Location', 'east');
title('Alea moral : plus on est couvert, moins on previent, plus il y a d accidents');
grid on;

La discrimination par les prix

Un monopole qui fait payer à chacun le prix maximum qu'il est prêt à mettre capture bien plus de valeur qu'avec un prix unique. Curieusement, cette discrimination parfaite est EFFICACE (elle supprime la perte sèche, tout le monde qui valorise le bien au-dessus du coût est servi), mais tout le surplus va à l'entreprise : les consommateurs n'en gardent rien. On suit le partage entre profit, surplus des consommateurs et perte sèche selon le degré de discrimination. Réglez le prix maximal du marché, le coût de production et le degré de discrimination.

Voir le code MATLAB
% Discrimination par les prix : prix unique vs discrimination parfaite
A = 100; c = 20;                       % prix max du marche, cout de production
Qm = (A-c)/2; Pm = (A+c)/2;            % monopole a prix unique
tot = 0.5*(A-c)^2;                     % surplus total possible (premier rang)
profitU  = (Pm-c)*Qm;
surplusU = 0.5*(A-Pm)*Qm;              % surplus des consommateurs
dwlU     = tot - profitU - surplusU;   % perte seche du prix unique
profitD = tot; surplusD = 0; dwlD = 0; % discrimination parfaite : tout au vendeur, 0 perte

figure;
bar([profitU surplusU dwlU; profitD surplusD dwlD], 'stacked');
set(gca, 'XTickLabel', {'Prix unique', 'Discrimination parfaite'});
ylabel('Valeur'); grid on;
legend('Profit', 'Surplus conso', 'Perte seche', 'Location', 'northeastoutside');
title('Discrimination parfaite : 0 perte seche, mais tout le surplus va au vendeur');

Taxe carbone ou quotas ?

Face au réchauffement, faut-il fixer un PRIX (taxe carbone) ou une QUANTITÉ (quotas échangeables) ? À l'optimum, les deux se valent. Mais quand le coût réel de la réduction est incertain, Martin Weitzman a montré que le choix dépend des pentes : si le bénéfice (le dommage évité) est plus pentu que le coût, mieux vaut garantir la quantité ; sinon, mieux vaut garantir le prix. Réglez les pentes et la surprise de coût.

Voir le code MATLAB
% Taxe carbone vs quotas (Weitzman) : prix contre quantite sous incertitude
A0 = 100; C0 = 10;          % benefice marginal a l'origine ; cout marginal a l'origine
bMB = 1.2; bMC = 1.2;       % pentes du benefice et du cout de reduction
shock = 20;                 % surprise sur les couts (cout reel plus eleve que prevu)

a = 0:0.5:60;               % abattement (reduction d'emissions)
MB  = A0 - bMB*a;           % benefice marginal (dommage evite)
MCe = C0 + bMC*a;           % cout marginal attendu
MCs = C0 + shock + bMC*a;   % cout marginal reel (avec la surprise)

Astar = (A0-C0)/(bMB+bMC); pstar = A0 - bMB*Astar;   % optimum attendu = quotas
Atrue = (A0-C0-shock)/(bMB+bMC);                      % optimum reel
Atax  = (pstar-C0-shock)/bMC;                         % abattement realise sous taxe

figure; hold on;
plot(a, MB,  'LineWidth', 2);
plot(a, MCe, 'LineWidth', 1.5);
plot(a, MCs, 'r--', 'LineWidth', 1.5);
plot([0 60], [pstar pstar], 'k:');                    % prix de la taxe
plot([Atrue Atrue], [0 A0], 'k:');                    % optimum reel
plot([Atax Atax],   [0 A0], 'color', [0.7 0.5 0.2]);  % resultat taxe
plot([Astar Astar], [0 A0], 'b:');                    % resultat quotas
xlabel('Abattement'); ylabel('Prix / cout par tonne');
legend('Benefice marginal', 'Cout attendu', 'Cout reel', 'Location', 'northeast');
title(sprintf('Optimum %.0f | taxe %.0f | quotas %.0f', Atrue, Atax, Astar));
grid on;

La courbe de coût d'abattement

Dans quel ordre décarboner, et à quel prix ? La courbe de coût d'abattement (MACC) classe les mesures de réduction du CO2 de la moins chère à la plus chère. Chaque barre : sa largeur est le CO2 évitable, sa hauteur le coût par tonne. Un prix du carbone rend rentables toutes les mesures situées sous son niveau. Fait remarquable : certaines mesures ont un coût négatif (elles font économiser). Réglez le prix du carbone.

Voir le code MATLAB
% Courbe de cout d'abattement marginal (MACC)
cost = [-45 -15 12 22 35 45 75 120 210];   % cout par tonne (euros/t), trie croissant
pot  = [8 7 12 14 6 9 10 7 5];             % potentiel d'abattement (Mt CO2)
p    = 60;                                 % prix du carbone

x = [0 cumsum(pot)];                       % bornes cumulees sur l'axe des x
figure; hold on;
for i = 1:numel(cost)
  col = [0.6 0.7 0.85];
  if cost(i) < 0, col = [0.3 0.7 0.5]; end          % mesures rentables en vert
  fill([x(i) x(i+1) x(i+1) x(i)], [0 0 cost(i) cost(i)], col);
end
plot([0 x(end)], [p p], 'r--', 'LineWidth', 1.5);     % prix du carbone
xlabel('Reduction cumulee (Mt CO2)'); ylabel('Cout par tonne (euros/t)');
title(sprintf('A %d euros/t, on adopte toutes les mesures sous la ligne rouge', p));
grid on;

Actualiser le futur

Combien vaut aujourd'hui un dommage climatique qui frappera dans un siècle ? Tout dépend du taux d'actualisation, qui convertit le futur en valeur présente. À un taux élevé, les dommages lointains pèsent presque zéro ; à un taux faible, ils comptent beaucoup. C'est le cœur du désaccord entre Nicholas Stern (taux bas, agir vite) et William Nordhaus (taux plus élevé). Réglez le taux, l'horizon et le montant du dommage.

Voir le code MATLAB
% Actualisation : valeur presente d'un dommage futur
D = 100;                       % dommage futur
r = 4.0;                       % votre taux d'actualisation (%)
T = 100;                       % horizon (annees)
t = 0:200;

vp    = D ./ (1+r/100).^t;     % votre taux
stern = D ./ (1+1.4/100).^t;   % taux bas (Stern)
nord  = D ./ (1+4.5/100).^t;   % taux eleve (Nordhaus)

figure; hold on;
plot(t, vp, 'LineWidth', 2);
plot(t, stern, '--', 'LineWidth', 1.2);
plot(t, nord,  '--', 'LineWidth', 1.2);
plot(T, D/(1+r/100)^T, 'o', 'MarkerFaceColor', 'r', 'MarkerSize', 8);
xlabel('Annees dans le futur'); ylabel('Valeur aujourd''hui');
legend('Votre taux', 'Stern 1.4%', 'Nordhaus 4.5%', 'Location', 'northeast');
title(sprintf('Un dommage de %d dans %d ans vaut %.1f aujourd''hui', D, T, D/(1+r/100)^T));
grid on;

Le coût social du carbone

Quel est le juste prix d'une tonne de CO2 ? Le coût social du carbone additionne, en valeur présente, tous les dommages futurs causés par une tonne émise aujourd'hui. Son estimation varie énormément, surtout selon le taux d'actualisation retenu : d'où des chiffres officiels allant de quelques dizaines à plus de 200 dollars la tonne. Réglez le taux, la croissance et la gravité des dommages.

Voir le code MATLAB
% Cout social du carbone : SCC = d0 / (r - g)  (perpetuite actualisee)
g   = 1.0;       % croissance des dommages (%)
dmg = 2.0;       % gravite des dommages
r   = 4.5;       % taux d'actualisation retenu (%)

rr  = 2:0.1:8;                        % taux d'actualisation (%)
SCC = 75*dmg ./ max(0.2, rr - g);     % cout social du carbone ($/t)

figure; hold on;
plot(rr, SCC, 'LineWidth', 2);
plot(r, 75*dmg/max(0.2, r-g), 'o', 'MarkerFaceColor', 'r', 'MarkerSize', 8);
xlabel('Taux d''actualisation (%)'); ylabel('Cout social du carbone ($/t)');
title(sprintf('SCC = %.0f $/t a %.1f%% (mais %.0f a 2.5%% et %.0f a 5%%)', ...
      75*dmg/max(0.2,r-g), r, 75*dmg/max(0.2,2.5-g), 75*dmg/max(0.2,5-g)));
grid on;

Macroéconomie

Les grands équilibres : monnaie, inflation, pouvoir d'achat.

Inflation & pouvoir d'achat

L'inflation ronge la valeur de l'argent : 100 € aujourd'hui n'achètent plus autant dans dix ans. La courbe pointillée suit la valeur nominale (le chiffre sur le compte), la courbe bleue le pouvoir d'achat réel. Si le rendement nominal ne dépasse pas l'inflation, le pouvoir d'achat s'érode. Règle des 70 : à i % d'inflation, le pouvoir d'achat est divisé par deux en environ 70 / i années.

Voir le code MATLAB
% Erosion du pouvoir d'achat par l'inflation
M = 1000; i = 0.02; g = 0.00; T = 20;    % montant, inflation, rendement nominal, horizon
t = 0:T;
nominal = M .* (1+g).^t;                  % valeur affichee sur le compte
reel    = M .* ((1+g)./(1+i)).^t;         % pouvoir d'achat reel
tauxReel = (1+g)/(1+i) - 1;               % taux reel annuel

figure; hold on;
plot(t, nominal, '--', 'LineWidth', 2);
plot(t, reel, 'LineWidth', 2);
xlabel('Annees'); ylabel('Valeur (euros)');
legend('Valeur nominale', 'Pouvoir d''achat reel', 'Location', 'northwest');
title(sprintf('Inflation %g%% : pouvoir d''achat divise par 2 en ~%.0f ans', i*100, 70/max(i*100,0.5)));
grid on;

La courbe de Laffer

À 0 % d'impôt, l'État ne récolte rien ; à 100 %, plus personne ne travaille ou ne déclare, donc rien non plus. Entre les deux, les recettes forment une cloche : il existe un taux qui les maximise. Déplacez le taux et la sensibilité des contribuables : au-delà du sommet, augmenter l'impôt fait BAISSER les recettes (« trop d'impôt tue l'impôt »).

Voir le code MATLAB
% Courbe de Laffer : recettes selon le taux d'imposition
B = 100; e = 1;             % base a taux nul, sensibilite des contribuables
t = 0:0.01:1;               % taux d'imposition
R = B .* t .* (1-t).^e;     % recettes fiscales
tStar = 1/(1+e);            % taux qui maximise les recettes
Rmax = B * tStar * (1-tStar)^e;

figure; hold on;
plot(t*100, R, 'LineWidth', 2);
plot(tStar*100, Rmax, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Taux d''imposition (%)'); ylabel('Recettes fiscales');
title(sprintf('Sommet a %.0f%% : au-dela, plus d''impot fait BAISSER les recettes', tStar*100));
grid on;

La courbe de Phillips

À court terme, il existe un arbitrage entre chômage et inflation : pousser l'activité pour faire baisser le chômage tend à accélérer les prix. Déplacez le chômage visé et lisez l'inflation correspondante le long de la courbe. Mais déplacez aussi les anticipations d'inflation : quand chacun s'attend à la hausse des prix, toute la courbe monte, et le même niveau de chômage coûte désormais plus d'inflation. C'est pourquoi l'arbitrage ne tient pas durablement.

Voir le code MATLAB
% Courbe de Phillips : arbitrage chomage / inflation
pe = 3;                          % anticipations d'inflation
u = 2:0.1:12;                    % taux de chomage (%)
pinf = pe + 20 .* (1./u - 1/8);  % inflation le long de la courbe

figure; hold on;
plot(u, pinf, 'LineWidth', 2);
plot(u, (pe+3) + 20.*(1./u - 1/8), '--');   % anticipations plus hautes : la courbe monte
xlabel('Taux de chomage (%)'); ylabel('Inflation (%)');
legend('Courbe de Phillips', 'Anticipations plus hautes', 'Location', 'northeast');
title('Phillips : arbitrage de court terme, qui se deplace avec les anticipations');
grid on;

Dette publique : l'effet boule de neige

Le poids de la dette (rapporté au PIB) évolue selon une course entre le taux d'intérêt payé et la croissance de l'économie. Si le taux dépasse la croissance, les intérêts font gonfler la dette plus vite que le pays ne s'enrichit : elle s'emballe même à budget équilibré. Il faut alors dégager un excédent primaire pour la stabiliser. Déplacez le taux, la croissance et le solde primaire, et regardez la trajectoire sur vingt ans.

Voir le code MATLAB
% Dette publique : effet boule de neige
b = 100; r = 0.03; g = 0.01; p = 0;   % dette/PIB, taux, croissance, solde primaire
for k = 1:20
    b(k+1) = b(k)*(1+r)/(1+g) - p;    % dynamique annuelle de la dette
end
pStar = 100*(r-g)/(1+g);              % excedent primaire pour stabiliser

figure; hold on;
plot(0:20, b, 'LineWidth', 2);
plot([0 20], [b(1) b(1)], 'k--');
xlabel('Annees'); ylabel('Dette (% du PIB)');
title(sprintf('r=%.0f%% vs g=%.0f%% : stabiliser demande un excedent primaire de %.1f%% du PIB', r*100, g*100, pStar));
grid on;

Le multiplicateur keynésien

Un euro dépensé par l'État devient un revenu pour quelqu'un, qui en redépense une partie, qui devient à son tour un revenu, et ainsi de suite en vagues de plus en plus petites. Au total, l'effet sur le PIB dépasse la dépense initiale : c'est le multiplicateur. Il est d'autant plus fort que les ménages consomment une large part de leur revenu ; l'épargne et les importations (les fuites) le réduisent. Déplacez la dépense et la propension à consommer, et regardez les vagues s'empiler.

Voir le code MATLAB
% Multiplicateur keynesien
G = 100; c = 0.6;           % depense initiale, propension a consommer
k = 1/(1-c);                % multiplicateur
total = G * k;              % effet total sur le PIB
vagues = G .* c.^(0:13);    % vagues de depense successives
cumule = cumsum(vagues);    % s'approche du total

figure; hold on;
bar(0:13, vagues, 'FaceColor', [0.55 0.62 0.72]);
plot(0:13, cumule, '-o', 'LineWidth', 2, 'Color', [0.20 0.45 0.70]);
plot([0 13], [total total], 'k--');
xlabel('Vagues de depense'); ylabel('Montant');
legend('Depense de chaque vague', 'Cumul', 'Effet total', 'Location', 'east');
title(sprintf('Multiplicateur = %.1f : %g depense donne %.0f de PIB', k, G, total));
grid on;

Le modèle de Solow : la croissance

Pourquoi un pays s'enrichit-il, et pourquoi sa croissance finit-elle par ralentir ? En épargnant, une économie accumule du capital par tête, mais chaque machine supplémentaire rapporte un peu moins que la précédente (rendements décroissants), pendant qu'une part du capital s'use et que la population grandit. La croissance s'arrête à l'équilibre k*, là où l'investissement s·f(k) croise juste l'amortissement (δ+n)·k. Déplacez les curseurs : épargner plus ou innover (A) élève le niveau de vie ; l'usure et la démographie l'abaissent.

Voir le code MATLAB
% Modele de Solow : capital par tete a l'equilibre
alpha = 1/3; A = 1; s = 0.25;          % part du capital, technologie, taux d'epargne
delta = 0.06; n = 0.01;                % depreciation, croissance demographique
kStar = (s*A/(delta+n))^(1/(1-alpha)); % etat stationnaire : s*A*k^alpha = (delta+n)*k
yStar = A*kStar^alpha;                 % production par tete
sGold = alpha;                         % regle d'or : le taux qui maximise la consommation

k = linspace(0, kStar*2.2, 200);
figure; hold on;
plot(k, A*k.^alpha, 'LineWidth', 2);          % production f(k)
plot(k, s*A*k.^alpha, 'LineWidth', 2);        % investissement s*f(k)
plot(k, (delta+n)*k, 'LineWidth', 2);         % amortissement (delta+n)*k
plot(kStar, s*A*kStar^alpha, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Capital par tete k'); ylabel('Par tete');
legend('Production f(k)', 'Investissement s*f(k)', 'Amortissement (d+n)k', 'Etat stationnaire', 'Location', 'northwest');
title(sprintf('Solow : k* = %.1f, y* = %.1f', kStar, yStar));
grid on;

Le modèle IS-LM : budget et monnaie

Comment l'État et la banque centrale agissent-ils sur l'activité à court terme ? La courbe IS réunit tous les couples (revenu, taux) qui équilibrent le marché des biens ; la courbe LM, ceux qui équilibrent le marché de la monnaie. Leur croisement fixe le revenu et le taux d'intérêt. Déplacez les curseurs : une relance budgétaire (dépenses G, impôts T) déplace IS, une relance monétaire (masse monétaire M/P) déplace LM.

Voir le code MATLAB
% Modele IS-LM : equilibre revenu/taux (prix fixes, court terme)
c = 0.6; C0 = 20; I0 = 40; b = 6;      % conso, invest. autonome, sensibilite au taux
k = 0.4; h = 5;                        % demande de monnaie : revenu, taux
G = 40; T = 30; M = 60;                % politiques : depenses, impots, monnaie reelle
A = C0 + I0 + G - c*T;                 % demande autonome
Ystar = (h*A + b*M) / (b*k + h*(1-c)); % revenu d'equilibre
istar = (k*Ystar - M) / h;             % taux d'interet d'equilibre

Y = linspace(0, 2*Ystar, 200);
figure; hold on;
plot(Y, (A - (1-c)*Y)/b, 'LineWidth', 2);   % IS (marche des biens)
plot(Y, (k*Y - M)/h, 'LineWidth', 2);       % LM (marche de la monnaie)
plot(Ystar, istar, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Revenu Y'); ylabel('Taux d''interet i');
legend('IS', 'LM', 'Equilibre', 'Location', 'northeast');
title(sprintf('IS-LM : Y* = %.0f, i* = %.1f', Ystar, istar));
grid on;

Offre et demande agrégées (AD-AS)

Comment se fixent, ensemble, la production d'un pays et le niveau général des prix ? La demande agrégée (AD) est décroissante, l'offre agrégée (AS) est croissante ; leur croisement donne l'équilibre. Déplacez les curseurs : une relance de la demande fait monter production et prix, mais un choc d'offre (une flambée du pétrole) déplace l'AS vers le haut, faisant monter les prix ET baisser la production, la fameuse stagflation. La verticale marque la production potentielle.

Voir le code MATLAB
% AD-AS : equilibre production / prix (court terme)
d = 2; s = 2; choc = 0;                % pentes AD/AS ; choc d'offre (0 = aucun, > 0 = flambee)
aD = 200; aS = 40 + choc; Ypot = 160;  % intercepts AD / AS, production potentielle
Ystar = (aD - aS) / (1/d + 1/s);       % production d'equilibre
Pstar = aD - Ystar/d;                  % niveau des prix d'equilibre
gap   = Ystar - Ypot;                  % ecart de production

Y = linspace(0, aD, 200);
figure; hold on;
plot(Y, aD - Y/d, 'LineWidth', 2);      % demande agregee (descendante)
plot(Y, aS + Y/s, 'LineWidth', 2);      % offre agregee (montante)
plot([Ypot Ypot], [0 aD], 'k--');       % production potentielle
plot(Ystar, Pstar, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Production Y'); ylabel('Niveau des prix P');
legend('Demande agregee', 'Offre agregee', 'Production potentielle', 'Equilibre', 'Location', 'northeast');
title(sprintf('AD-AS : Y* = %.0f, P* = %.0f (un choc d''offre monte AS : stagflation)', Ystar, Pstar));
grid on;

Les inégalités : Lorenz et Gini

Comment mesurer les inégalités de revenu d'un seul chiffre ? La courbe de Lorenz relie la part cumulée de la population (des plus pauvres aux plus riches) à la part cumulée des revenus. Si tout le monde gagnait la même chose, elle suivrait la diagonale. Plus elle s'en éloigne, plus les revenus sont concentrés. Le coefficient de Gini résume cet écart entre 0 (égalité parfaite) et 1 (une seule personne possède tout). Déplacez le curseur de concentration.

Voir le code MATLAB
% Courbe de Lorenz stylisee L(p) = p^k et coefficient de Gini
k = 2;                                 % concentration (k = 1 : egalite parfaite)
p = linspace(0,1,101);
L = p.^k;                              % part cumulee des revenus
gini = (k-1)/(k+1);                    % = 2 * aire entre la diagonale et Lorenz
top20 = 1 - 0.8^k;   bot20 = 0.2^k;    % parts des 20% les + riches / + pauvres

figure; hold on;
fill([p fliplr(p)], [p fliplr(L)], [0.55 0.62 0.72], 'FaceAlpha', 0.25, 'EdgeColor', 'none');  % aire de Gini
plot(p, L, 'LineWidth', 2);            % courbe de Lorenz
plot([0 1], [0 1], 'k--');             % egalite parfaite
xlabel('Part cumulee de la population'); ylabel('Part cumulee des revenus');
legend('Aire de Gini', 'Courbe de Lorenz', 'Egalite parfaite', 'Location', 'northwest');
title(sprintf('Gini = %.2f  (0 = egalite, 1 = une personne a tout)', gini));
axis square; grid on;

La courbe de Kuznets

Les inégalités augmentent-elles ou baissent-elles quand un pays se développe ? Kuznets a proposé un U inversé : au début de l'industrialisation, une partie de la population passe à des emplois modernes bien mieux payés pendant que le reste stagne dans l'agriculture, et les inégalités MONTENT. Puis, à mesure que la transition se généralise, l'écart se resserre et les inégalités REDESCENDENT. Réglez l'écart de revenu entre secteurs, l'effort de redistribution et le niveau de développement du pays.

Voir le code MATLAB
% Courbe de Kuznets : inegalites selon le developpement (U inverse)
gap = 0.5;                             % ecart de revenu entre secteurs
redis = 0.2;                           % effort de redistribution
dev = linspace(0, 1, 200);             % niveau de developpement
ineq = gap*4 .* dev .* (1 - dev) - redis*dev;   % monte puis redescend

figure;
plot(dev*100, max(0, ineq), 'LineWidth', 2);
xlabel('Niveau de developpement (%)'); ylabel('Inegalites (indice)');
title('Kuznets : les inegalites montent puis redescendent avec le developpement');
grid on;

Mundell-Fleming : l'économie ouverte

Que devient IS-LM quand les capitaux circulent librement entre pays ? On ajoute la droite BP, horizontale au taux d'intérêt mondial : à l'équilibre, le taux interne doit y revenir, sinon les capitaux affluent ou fuient et font bouger le change. Le grand enseignement : en changes flottants, la politique monétaire est puissante et la budgétaire s'évince toute seule par le taux de change ; en changes fixes, c'est exactement l'inverse. Déplacez le budget, la monnaie et le taux mondial.

Voir le code MATLAB
% Mundell-Fleming : IS-LM + BP horizontale au taux mondial i*
c=0.6; C0=20; I0=40; b=6; k=0.4; h=5; T=30;
G=40; M=60; iStar=4;                    % budget, monnaie, taux mondial
A = C0 + I0 + G - c*T;
Ystar = (h*A + b*M)/(b*k + h*(1-c));    % revenu interne (IS-LM)
iInt  = (k*Ystar - M)/h;               % taux interne
% i interne au-dessus du mondial : entree de capitaux ; en dessous : sortie

Y = linspace(0, 2*Ystar, 200);
figure; hold on;
plot(Y, (A - (1-c)*Y)/b, 'LineWidth', 2);                 % IS
plot(Y, (k*Y - M)/h, 'LineWidth', 2);                     % LM
plot([0 2*Ystar], [iStar iStar], '--', 'LineWidth', 2);   % BP (taux mondial)
plot(Ystar, iInt, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
xlabel('Revenu Y'); ylabel('Taux d''interet i');
legend('IS', 'LM', 'BP (taux mondial i*)', 'Equilibre interne', 'Location', 'northeast');
title(sprintf('Mundell-Fleming : i interne %.1f vs mondial %g (flux de capitaux)', iInt, iStar));
grid on;

Dornbusch : le surajustement du change

Après une hausse permanente de la masse monétaire, à quoi ressemble le chemin du taux de change ? À court terme, les prix sont rigides : la monnaie réelle augmente, le taux d'intérêt chute. Pour que les capitaux ne fuient pas (parité des taux d'intérêt), la monnaie doit être attendue en appréciation... ce qui n'est possible que si elle se déprécie d'abord au-delà de sa valeur de long terme. Le change surréagit : il bondit trop haut, puis revient lentement vers l'équilibre pendant que les prix montent. C'est le célèbre surajustement de Dornbusch. Déplacez la rigidité des prix : plus les prix sont lents, plus la surréaction est forte.

Voir le code MATLAB
% Dornbusch : surajustement (overshooting) du taux de change
m = 10; theta = 0.5; phi = 2;      % choc monetaire %, vitesse des prix, sensibilite demande monnaie
over = m/(phi*theta);              % surreaction : le change depasse le long terme
t = linspace(-3, 20, 600);
pos = t >= 0;
E = zeros(size(t)); P = zeros(size(t));
E(pos) = m + over*exp(-theta*t(pos));   % le change saute a m+over puis revient vers m
P(pos) = m*(1 - exp(-theta*t(pos)));    % les prix montent lentement vers m

figure; hold on;
plot(t, E, 'LineWidth', 2);        % taux de change (overshoot)
plot(t, P, 'LineWidth', 2);        % niveau des prix
plot([-3 20], [m m], '--k');       % niveau de long terme
xlabel('Temps'); ylabel('Ecart au niveau initial (%)');
legend('Taux de change', 'Niveau des prix', 'Long terme', 'Location', 'east');
title(sprintf('Overshooting : le change saute a %.1f%% puis revient a %.1f%%', m+over, m));
grid on;

La croissance endogène

Dans le modèle de Solow, la croissance finit par s'essouffler : le capital subit des rendements décroissants. Mais si le savoir se diffuse (recherche, éducation, effets d'apprentissage), le capital peut ne PLUS être décroissant : l'investissement devient une droite. S'il dépasse l'usure, l'écart se creuse indéfiniment et la croissance s'auto-entretient, sans progrès technique venu de l'extérieur. Déplacez l'épargne, la productivité du savoir et l'usure.

Voir le code MATLAB
% Croissance endogene (modele AK) : Y = A*K (pas de rendements decroissants)
s = 0.25; A = 0.3; dn = 0.045;         % epargne, productivite du savoir, usure + demographie
g = s*A - dn;                          % taux de croissance, CONSTANT et positif si s*A depasse dn

k = linspace(0, 100, 200);
figure; hold on;
plot(k, s*A*k, 'LineWidth', 2);        % investissement : une DROITE (vs courbe concave chez Solow)
plot(k, dn*k, 'LineWidth', 2);         % usure (d+n)*k
xlabel('Capital par tete k'); ylabel('Par tete');
legend('Investissement s*A*k', 'Usure (d+n)*k', 'Location', 'northwest');
title(sprintf('AK : l''ecart se creuse sans fin, croissance g = %.1f%%', g*100));
grid on;

La règle de Taylor

Comment une banque centrale fixe-t-elle son taux directeur ? John Taylor a résumé sa pratique en une règle simple : partir d'un taux neutre, puis le relever quand l'inflation dépasse sa cible et quand l'économie surchauffe. Point clé (le « principe de Taylor ») : face à l'inflation, la banque doit monter son taux PLUS que proportionnellement, sinon le taux réel baisse et l'inflation s'emballe. On trace le taux prescrit selon l'inflation. Réglez l'inflation, l'écart de production et l'agressivité de la réponse.

Voir le code MATLAB
% Regle de Taylor : taux directeur prescrit selon l'inflation
rNeutre = 1; cible = 2; phiPi = 0.5; gap = 0;   % taux neutre, cible, agressivite, ecart de production
pig = linspace(0, 6, 200);                      % inflation (%)
taux = rNeutre + pig + phiPi*(pig - cible) + 0.5*gap;   % taux prescrit

figure; hold on;
plot(pig, taux, 'LineWidth', 2);
plot(pig, pig, 'k--');                          % droite a 45 degres (taux = inflation)
xlabel('Inflation (%)'); ylabel('Taux directeur (%)');
legend('Taux prescrit (Taylor)', 'Inflation (45 degres)', 'Location', 'northwest');
title('Principe de Taylor : une pente superieure a 1 fait monter le taux REEL avec l''inflation');
grid on;

La création monétaire

D'où vient la monnaie ? L'essentiel n'est pas imprimé par la banque centrale : il est créé par les banques commerciales quand elles prêtent. Une injection de monnaie centrale revient en dépôt, la banque en reprête une partie, qui revient en dépôt... À chaque tour, une fraction fuit (réserves obligatoires, billets gardés), si bien que le total converge : c'est le multiplicateur de crédit. Réglez le taux de réserve et la préférence pour les billets.

Voir le code MATLAB
% Creation monetaire : le multiplicateur de credit
B = 100;                        % injection de monnaie centrale
r = 0.10;                       % taux de reserve
b = 0.00;                       % preference pour les billets (fuite)
q = (1 - r)*(1 - b);            % fraction re-deposee a chaque tour
N = 0:20;

parTour = B * q.^N;                       % monnaie creee a chaque tour
cumul   = B * (1 - q.^(N+1)) / (1 - q);   % monnaie cumulee
total   = B / (1 - q);                    % limite : multiplicateur = 1/(1-q)

figure; hold on;
bar(N, parTour);                          % monnaie creee tour par tour
plot(N, cumul, 'LineWidth', 2);           % cumul qui converge
plot([0 20], [total total], 'r--');       % asymptote (monnaie totale)
xlabel('Tour de pret'); ylabel('Monnaie');
legend('Cree par tour', 'Cumul', 'Monnaie totale', 'Location', 'east');
title(sprintf('Multiplicateur = %.1f  ->  monnaie totale = %.0f', total/B, total));
grid on;

Le bilan de la banque centrale (QE)

Que fait vraiment un « assouplissement quantitatif » (QE) ? La banque centrale achète des actifs (surtout des obligations d'État) et les paie en créant des réserves : à l'actif les titres, au passif les réserves. Les deux côtés du bilan gonflent ensemble. L'objectif est de faire baisser les taux longs et de pousser les banques à prêter. Réglez le montant des achats et la demande de billets, et regardez le bilan enfler.

Voir le code MATLAB
% Bilan de la banque centrale : effet du QE (achats d'actifs)
T0 = 1500; LEND = 800; GOLD = 700; K = 100;    % postes fixes (Md)
qe  = 1000;                                     % achats d'actifs (QE)
ban = 1400;                                     % billets en circulation
reserves = (T0 + qe + LEND + GOLD) - ban - K;   % reserves = poste d'ajustement

actif  = [T0 qe LEND GOLD];      % Titres, QE, Prets, Or&devises
passif = [ban reserves K 0];     % Billets, Reserves, Capital
M = [actif; passif];             % 2 barres empilees (actif = passif)

figure;
bar(M, 'stacked');
set(gca, 'XTickLabel', {'Actif', 'Passif'});
ylabel('Milliards');
legend('Titres / Billets', 'QE / Reserves', 'Prets / Capital', 'Or&devises', 'Location', 'eastoutside');
title(sprintf('Bilan = %.0f Md : le QE cree des reserves', T0+qe+LEND+GOLD));
grid on;

La théorie quantitative (MV = PY)

Trop de monnaie fait-il monter les prix ? L'équation des échanges MV = PY relie la masse monétaire (M), sa vitesse de circulation (V), le niveau des prix (P) et la production réelle (Y). En taux de croissance : inflation = croissance de la monnaie + variation de la vitesse - croissance réelle. L'excès de monnaie sur la capacité de production se déverse dans les prix, jusqu'à l'hyperinflation. Réglez les trois leviers.

Voir le code MATLAB
% Theorie quantitative : MV = PY
% inflation = croissance monnaie + var. vitesse - croissance reelle
g  = 2;      % croissance reelle (%)
dv = 0;      % variation de la vitesse (%)
mg = 8;      % croissance de la masse monetaire retenue (%)

x  = 0:1:60;             % croissance monetaire (%)
inflation = x + dv - g;  % inflation prescrite par MV=PY

figure; hold on;
plot(x, inflation, 'LineWidth', 2);
plot(x, x, 'k--');                                    % 45 degres : inflation = monnaie
plot(mg, mg + dv - g, 'o', 'MarkerFaceColor', 'r', 'MarkerSize', 8);
xlabel('Croissance de la masse monetaire (%)'); ylabel('Inflation (%)');
legend('Inflation (MV=PY)', 'inflation = monnaie (45)', 'Point courant', 'Location', 'northwest');
title(sprintf('Monnaie +%d%%, reel +%.1f%%  ->  inflation ~ %.1f%%', mg, g, mg+dv-g));
grid on;

L'incohérence temporelle

Pourquoi vaut-il mieux une banque centrale indépendante ? Une banque tentée de doper l'emploi promet une inflation basse, puis triche en créant la surprise d'inflation. Mais les agents l'anticipent : l'inflation attendue monte jusqu'à ce que la banque n'ait plus intérêt à surprendre. Résultat, le fameux « biais inflationniste » de Kydland et Prescott : de l'inflation en plus, sans aucun gain d'emploi. Réglez l'ambition de la banque et sa tentation.

Voir le code MATLAB
% Incoherence temporelle (Kydland-Prescott) : le biais inflationniste
lam = 1.0;    % poids donne a l'emploi
a   = 0.7;    % pente de la courbe de Phillips
k   = 2;      % ambition : chomage vise sous le naturel (points)

x = 0:0.1:4;                  % ambition
discretion = lam * a * x;     % inflation d'equilibre sous discretion
engagement = zeros(size(x));  % inflation sous engagement credible (regle)

figure; hold on;
plot(x, discretion, 'LineWidth', 2);
plot(x, engagement, 'LineWidth', 2);
plot(k, lam*a*k, 'o', 'MarkerFaceColor', 'r', 'MarkerSize', 8);
xlabel('Ambition (chomage vise sous le naturel)'); ylabel('Inflation d''equilibre (%)');
legend('Discretion', 'Engagement (regle)', 'Point courant', 'Location', 'northwest');
title(sprintf('Biais inflationniste = %.1f%% (aucun gain d''emploi)', lam*a*k));
grid on;

Le capital humain

Pourquoi les diplômés gagnent-ils plus ? L'équation de Jacob Mincer explique le salaire par le capital humain : les années d'études et l'expérience. Chaque année d'études rapporte un pourcentage de salaire en plus, toute la carrière ; l'expérience ajoute un gain, mais qui s'épuise (profil concave). On compare deux niveaux d'études. Réglez le rendement des études, le niveau d'études et la prime d'expérience.

Voir le code MATLAB
% Capital humain : equation de Mincer (salaire selon etudes et experience)
W0 = 800; rho = 9; b1 = 0.04; b2 = 0.0007;    % base, rendement etudes (%), prime exp., concavite
X = 0:40;                                      % annees d'experience
S1 = 14; S2 = 10;                              % deux niveaux d'etudes

w1 = W0 * exp(rho/100*S1 + b1*X - b2*X.^2);
w2 = W0 * exp(rho/100*S2 + b1*X - b2*X.^2);

figure; hold on;
plot(X, w1, 'LineWidth', 2);
plot(X, w2, 'LineWidth', 2);
xlabel('Annees d''experience'); ylabel('Salaire mensuel (euros)');
legend(sprintf('%d ans d''etudes', S1), sprintf('%d ans d''etudes', S2), 'Location', 'southeast');
title(sprintf('Mincer : +1 an d''etudes = environ +%.1f%% de salaire', 100*(exp(rho/100)-1)));
grid on;

r > g : la dynamique du patrimoine

Pourquoi les grandes fortunes prennent-elles le large ? Thomas Piketty résume : quand le rendement du capital (r) dépasse durablement la croissance de l'économie (g), le patrimoine déjà accumulé grossit plus vite que les revenus du travail, surtout par l'héritage. On suit un patrimoine placé et l'économie, indexés à 100. Réglez le rendement du capital, la croissance et le taux d'épargne.

Voir le code MATLAB
% r > g : le patrimoine croit plus vite que l'economie (Piketty)
r = 5; g = 1.5; s = 10;        % rendement capital (%), croissance (%), taux d'epargne (%)
t = 0:50;

patrimoine = 100 * (1+r/100).^t;
economie   = 100 * (1+g/100).^t;
beta = s/g;                    % 2e loi : capital/revenu de long terme

figure; hold on;
plot(t, patrimoine, 'LineWidth', 2);
plot(t, economie, 'LineWidth', 2);
xlabel('Annees'); ylabel('Indice (base 100)');
legend('Patrimoine (r)', 'Economie (g)', 'Location', 'northwest');
title(sprintf('r - g = %+.1f pts | capital/revenu beta = s/g = %.1f', r-g, beta));
grid on;

La courbe de Beveridge

Peut-il y avoir beaucoup de chômeurs ET beaucoup d'emplois vacants en même temps ? La courbe de Beveridge relie les deux : normalement, quand l'un monte l'autre baisse (c'est la conjoncture). Mais si les deux montent ensemble, c'est que la courbe s'est déplacée : un problème d'appariement (compétences ou lieux qui ne correspondent pas). Réglez l'efficacité d'appariement et la conjoncture.

Voir le code MATLAB
% Courbe de Beveridge : chomage vs emplois vacants
eff = 1;                       % efficacite d'appariement
K = 24 / eff;                  % position de la courbe (plus grand = moins efficace)
u = 2:0.1:14;                  % taux de chomage (%)
v = K ./ u;                    % taux d'emplois vacants (%)

cycle = 50;                    % position dans le cycle (0 expansion, 100 recession)
uPt = 3 + cycle/100*8; vPt = K/uPt;

figure; hold on;
plot(u, v, 'LineWidth', 2);
plot(uPt, vPt, 'o', 'MarkerFaceColor', 'r', 'MarkerSize', 8);
xlim([0 14]); ylim([0 14]);
xlabel('Taux de chomage (%)'); ylabel('Taux d''emplois vacants (%)');
title('Beveridge : le long = conjoncture, deplacement = appariement');
grid on;

La courbe du Grand Gatsby

Naît-on plus facilement riche ou pauvre selon le pays ? La courbe du Grand Gatsby relie l'inégalité (coefficient de Gini) à l'immobilité sociale (à quel point le revenu des parents prédit celui des enfants). Chaque point est un pays : plus une société est inégalitaire, moins on y monte l'échelle sociale. Réglez le niveau d'inégalité pour lire la mobilité prédite.

Voir le code MATLAB
% Courbe du Grand Gatsby : inegalite (Gini) vs immobilite (elasticite intergenerationnelle)
gini = [25 26 27 30 32 32 33 36 36 41 53];
ige  = [0.15 0.18 0.17 0.32 0.19 0.34 0.41 0.48 0.50 0.47 0.66];

gLine = 20:58;
fit = -0.20 + 0.0155*gLine;    % tendance croissante

figure; hold on;
scatter(gini, ige, 60, 'filled');
plot(gLine, fit, '--', 'LineWidth', 1.5);
xlabel('Inegalite (coefficient de Gini)'); ylabel('Persistance (moins de mobilite)');
legend('Pays', 'Tendance', 'Location', 'northwest');
title('Plus une societe est inegalitaire, moins la mobilite sociale est forte');
grid on;

Marchés & finance

Les modèles qui font tourner les marchés financiers : options, portefeuilles, risque.

Black-Scholes : le prix d'une option

Le modèle de Black, Scholes et Merton (1973) donne le prix théorique d'une option européenne : le droit d'acheter (call) ou de vendre (put) un actif à un prix fixé d'avance (le strike K). Faites varier les paramètres : la courbe bleue montre le prix du call selon le cours du sous-jacent, la pointillée orange son payoff à maturité, et la ligne grise marque le cours actuel S.

Voir le code MATLAB
function [call, put] = black_scholes(S, K, T, sigma, r)
% BLACK_SCHOLES  Prix d'une option europeenne (call et put)
    d1 = (log(S/K) + (r + sigma^2/2)*T) / (sigma*sqrt(T));
    d2 = d1 - sigma*sqrt(T);
    call = S*normcdf(d1) - K*exp(-r*T)*normcdf(d2);
    put  = K*exp(-r*T)*normcdf(-d2) - S*normcdf(-d1);
end

% Exemple : courbe du prix du call selon le sous-jacent
S = 40:1:160;
[call, ~] = arrayfun(@(s) black_scholes(s, 100, 1, 0.2, 0.03), S);
plot(S, call, 'LineWidth', 2); hold on
plot(S, max(S - 100, 0), '--');
xlabel('Cours du sous-jacent'); ylabel('Prix du call');
legend('Prix Black-Scholes', 'Payoff a maturite');

Markowitz : la frontière d'efficience

Harry Markowitz (1952) a montré qu'en combinant des actifs imparfaitement corrélés, on réduit le risque sans sacrifier le rendement : c'est la diversification. Chaque point bleu est un portefeuille possible (sans vente à découvert), la courbe foncée relie les meilleurs d'entre eux, et l'étoile orange marque le portefeuille au ratio de Sharpe maximal (taux sans risque : 2 %). Baissez les corrélations : la frontière s'envole vers la gauche.

Voir le code MATLAB
% Frontiere d'efficience de Markowitz (3 actifs, sans vente a decouvert)
mu    = [0.08; 0.03; 0.06];          % rendements attendus
sigma = [0.18; 0.05; 0.25];          % volatilites
rho   = [1 0.2 0.1; 0.2 1 0.3; 0.1 0.3 1];
Sigma = (sigma*sigma') .* rho;       % matrice de covariance

n = 5000;                            % portefeuilles aleatoires
W = -log(rand(n, 3));
W = W ./ sum(W, 2);                  % poids positifs, somme = 1
ret = W * mu;
vol = sqrt(sum((W*Sigma) .* W, 2));

scatter(vol, ret, 8, (ret - 0.02)./vol, 'filled'); hold on
xlabel('Risque (volatilite)'); ylabel('Rendement attendu');
title('Frontiere d''efficience de Markowitz');

Markowitz sur données réelles

La même frontière, mais calculée sur les vrais cours de votre panier (180 derniers jours, source Twelve Data). Rendements et risques annualisés.

Voir le code MATLAB
% Frontiere de Markowitz a partir de rendements/covariances estimes (donnees reelles)
mu = [0.08; 0.12; 0.15];                       % rendements attendus des actifs
S  = [0.04 0.01 0.00; 0.01 0.09 0.02; 0.00 0.02 0.16];   % matrice de covariance
n = 20000; R = zeros(n,1); V = zeros(n,1);
for i = 1:n
  w = rand(3,1); w = w/sum(w);                 % portefeuille aleatoire (poids positifs, somme 1)
  R(i) = w'*mu; V(i) = sqrt(w'*S*w);
end
figure;
scatter(V*100, R*100, 6, 'filled');
xlabel('Risque (volatilite, %)'); ylabel('Rendement attendu (%)');
title('Nuage de portefeuilles : le bord superieur gauche est la frontiere efficiente');
grid on;

Monte-Carlo : trajectoires de prix

La plupart des modèles de marché supposent que le cours d'un actif suit un mouvement brownien géométrique : à chaque instant, une tendance moyenne (le rendement) plus un choc aléatoire proportionnel à la volatilité. On simule ici des dizaines de trajectoires à partir des mêmes chocs : la bande colorée montre l'intervalle où le prix a 90 % de chances de se trouver, la courbe foncée la trajectoire médiane, et l'histogramme la distribution du prix final. C'est le moteur qui se cache derrière Black-Scholes.

Voir le code MATLAB
function paths = gbm_paths(S0, mu, sigma, T, nSteps, nPaths)
% GBM_PATHS  Trajectoires de prix par mouvement brownien geometrique
    dt   = T / nSteps;
    Z    = randn(nPaths, nSteps);
    incr = (mu - sigma^2/2)*dt + sigma*sqrt(dt)*Z;
    paths = S0 * exp([zeros(nPaths,1), cumsum(incr, 2)]);
end

% Exemple : 200 trajectoires sur 1 an + bande de confiance a 90 %
P = gbm_paths(100, 0.08, 0.20, 1, 52, 200);
t = linspace(0, 1, 53);
plot(t, P', 'Color', [0.6 0.7 0.9]); hold on
plot(t, quantile(P, [0.05 0.5 0.95]), 'LineWidth', 2);
xlabel('Temps (annees)'); ylabel('Prix');
title('Monte-Carlo : trajectoires de prix');

MEDAF : la droite de marché

Le MEDAF (CAPM) répond à une question simple : quel rendement exiger d'un actif compte tenu de son risque ? Pas n'importe quel risque, seulement le risque non diversifiable, mesuré par le bêta (la sensibilité aux mouvements du marché). La droite de marché des titres (SML) relie ce bêta au rendement attendu : E[R] = rf + β (Rm − rf). Un actif au-dessus de la droite rapporte plus que ce que son risque justifie (sous-évalué, alpha positif) ; en dessous, il est cher payé (surévalué). C'est l'extension naturelle de Markowitz : on ajoute un actif sans risque, et le meilleur portefeuille risqué devient le portefeuille de marché.

Voir le code MATLAB
function [er, alpha] = capm(beta, rf, Rm, Robs)
% CAPM  Rendement attendu (SML) et alpha de Jensen
    er    = rf + beta .* (Rm - rf);   % droite de marche des titres
    alpha = Robs - er;                % sur/sous-evaluation
end

% Exemple : SML + trois actifs
rf = 0.02; Rm = 0.08;
beta = 0:0.05:2;
plot(beta, rf + beta*(Rm - rf), 'LineWidth', 2); hold on
b = [0.6 1.0 1.6]; R = [0.07 0.08 0.10];
scatter(b, R, 60, 'filled');
plot(1, Rm, 'p', 'MarkerSize', 14);     % portefeuille de marche
xlabel('Beta'); ylabel('Rendement attendu');
title('Droite de marche des titres (SML)');

Obligations : prix contre taux

Une obligation verse un coupon fixe puis rembourse sa valeur à l'échéance. Quand les taux du marché montent, les obligations déjà émises, au coupon devenu trop bas, valent moins : leur prix baisse (et inversement). Plus l'échéance est lointaine, plus ce prix est sensible au taux : c'est la duration. Déplacez le taux de marché, l'échéance et le coupon pour voir le prix se déformer et mesurer l'effet d'une hausse d'un point de taux.

Voir le code MATLAB
% Obligation : prix contre taux, duration
F = 100; cpn = 0.03; T = 10; y = 0.03;   % nominal, coupon, echeance, taux
t = (1:T)';
CF = cpn*F*ones(T,1); CF(T) = CF(T) + F;     % flux : coupons + nominal a T
prix = sum(CF ./ (1+y).^t);
macaulay = sum(t .* CF ./ (1+y).^t) / prix;
durationMod = macaulay / (1+y);              % sensibilite du prix au taux

yv = linspace(0.005, 0.10, 200);
pv = arrayfun(@(r) sum(CF ./ (1+r).^t), yv);
figure; hold on;
plot(yv*100, pv, 'LineWidth', 2);
plot(y*100, prix, 'o', 'MarkerSize', 8, 'MarkerFaceColor', [0.80 0.20 0.15]);
plot([0.5 10], [F F], 'k--');                % valeur nominale (pair)
xlabel('Taux de marche (%)'); ylabel('Prix de l''obligation');
legend('Prix', 'Taux actuel', 'Valeur nominale', 'Location', 'northeast');
title(sprintf('Prix = %.1f ; duration modifiee = %.1f (le prix baisse si le taux monte)', prix, durationMod));
grid on;

La courbe des taux

Pourquoi un prêt à 10 ans ne rapporte-t-il pas le même taux qu'un prêt à 3 mois ? La courbe des taux relie le rendement à l'échéance. Elle reflète surtout ce que le marché anticipe pour les taux courts futurs, plus une prime pour immobiliser son argent longtemps. Normalement elle monte ; mais quand le marché anticipe des BAISSES de taux (souvent avant une récession), elle s'INVERSE, le court dépassant le long. Réglez le taux court actuel, le niveau anticipé à long terme et la prime de terme.

Voir le code MATLAB
% Courbe des taux : rendement selon l'echeance
short = 4.5; longRun = 3.0; premium = 0.5;   % taux court actuel, niveau anticipe, prime de terme
n = 0.25:0.25:10;                            % echeances (annees)
y = longRun + (short-longRun).*exp(-n/3) + premium*(1 - exp(-n/3));

figure; hold on;
plot(n, y, 'LineWidth', 2);
plot([0 10], [short short], 'k--');
xlabel('Echeance (annees)'); ylabel('Rendement (%)');
legend('Courbe des taux', 'Taux court actuel', 'Location', 'northeast');
if y(end) - y(1) < 0, forme = 'INVERSEE (signal de recession)'; else forme = 'normale (ascendante)'; end
title(['Courbe des taux : ' forme]);
grid on;

Les bulles spéculatives

Une bulle, c'est un prix qui s'envole au-dessus de la valeur fondamentale, porté par la seule anticipation qu'il montera encore, jusqu'au krach. Pour qu'on accepte de la détenir malgré le risque d'éclatement, la bulle doit gonfler d'autant plus vite que ce risque est élevé (condition de non-arbitrage) : plus elle enfle, plus la chute est brutale. On suit le prix qui s'envole puis s'effondre à la valeur fondamentale. Réglez le rythme de gonflement, la probabilité de krach et le rendement exigé.

Voir le code MATLAB
% Bulle speculative : gonflement puis krach a la valeur fondamentale
F = 100; g = 0.12; pcrash = 0.05;      % valeur fondamentale, rythme de gonflement, proba de krach
tBurst = round(1/pcrash);              % eclatement attendu (periodes)
t = 0:tBurst;
price = F*(1+g).^t;                    % la bulle enfle

figure; hold on;
plot(t, price, 'LineWidth', 2);
plot([0 tBurst], [F F], 'k--');                             % valeur fondamentale
plot([tBurst tBurst], [price(end) F], 'r', 'LineWidth', 2); % krach
xlabel('Temps (periodes)'); ylabel('Prix');
legend('Prix de la bulle', 'Valeur fondamentale', 'Krach', 'Location', 'northwest');
title(sprintf('Krach attendu vers t=%d, effacant %.0f%% du prix', tBurst, (price(end)-F)/price(end)*100));
grid on;

La ruée bancaire

Une banque promet de rendre l'argent à vue, mais l'a prêté à long terme : elle ne peut pas tout rembourser d'un coup sans brader ses prêts. Si trop de déposants retirent en même temps, même une banque saine s'effondre. On fait varier la part des déposants qui retirent tôt et on regarde ce que récupère un déposant patient : sous un certain seuil la banque tient ; au-dessus, la panique s'auto-réalise. Réglez les réserves liquides, la décote de liquidation et le rendement des prêts.

Voir le code MATLAB
% Ruee bancaire (Diamond-Dybvig) : recuperation selon la part qui retire tot
rho = 0.15; h = 0.40; Rg = 1.20;       % reserves liquides, decote, rendement brut des prets
D = 100; f = linspace(0, 1, 200);
c1 = zeros(size(f)); c2 = zeros(size(f));
for j = 1:numel(f)
  need = f(j)*D; L0 = rho*D; I0 = (1-rho)*D;
  faceRem = I0 - max(0, need - L0)/(1-h);      % prets restants apres vente en catastrophe
  if faceRem >= 0
    c1(j) = 1;
    c2(j) = (Rg*faceRem + max(0, L0-need)) / max(1e-9, (1-f(j))*D);
  else
    c1(j) = (L0 + I0*(1-h))/need;  c2(j) = 0;
  end
end
figure; hold on;
plot(f*100, c2, 'LineWidth', 2);       % deposant patient
plot(f*100, c1, '--', 'LineWidth', 2); % retrait anticipe
plot([0 100], [1 1], 'k:');            % retirer maintenant = 1
xlabel('Part des deposants qui retirent tot (%)'); ylabel('Recupere par unite');
legend('Deposant patient', 'Retrait anticipe', 'Retirer maintenant = 1', 'Location', 'northeast');
title('Ruee : sous un seuil la banque tient, au-dessus la panique s auto-realise');
grid on;

L'effet de levier

Acheter un actif avec une mise (les fonds propres) complétée par de la dette, c'est le levier : il multiplie le rendement, à la hausse comme à la baisse. Une petite baisse du prix peut effacer toute la mise ; et quand les fonds propres passent sous la marge de maintenance, l'appel de marge force à vendre au pire moment, c'est la spirale de désendettement. Réglez le levier, le choc de prix et la marge de maintenance.

Voir le code MATLAB
% Effet de levier : rendement des fonds propres = levier x variation du prix
lev = 4; mm = 0.15;                    % levier, marge de maintenance
dp = linspace(-50, 30, 200);           % variation du prix de l'actif (%)
eqRet = lev*dp;                        % rendement des fonds propres (%)
dpCall = (mm - 1/lev)/(1-mm)*100;      % seuil d'appel de marge

figure; hold on;
plot(dp, eqRet, 'LineWidth', 2);       % avec levier
plot(dp, dp, '--');                    % sans levier
plot([-50 30], [-100 -100], 'r:');     % fonds propres effaces
xlabel('Variation du prix de l''actif (%)'); ylabel('Rendement des fonds propres (%)');
legend('Avec levier', 'Sans levier', 'Fonds propres effaces', 'Location', 'northwest');
title(sprintf('Levier x%.0f : une baisse de %.0f%% efface la mise ; appel de marge des %.0f%%', lev, 100/lev, dpCall));
grid on;

Le prêteur en dernier ressort

Une banque solvable (ses actifs valent plus que ses dettes à terme) peut malgré tout faire faillite si elle manque de liquidités et doit brader ses actifs à perte. Le prêteur en dernier ressort (la banque centrale) lui avance alors des liquidités contre garanties, pour éviter la vente forcée. On compare ce que récupèrent les déposants avec et sans prêteur, et on voit pourquoi Bagehot le réserve aux banques solvables. Réglez la valeur des actifs, la décote et l'ampleur des retraits.

Voir le code MATLAB
% Preteur en dernier ressort (Bagehot) : recuperation sans vs avec preteur
Vm = 110; h = 0.40; w = 50; PEN = 0.05;   % actifs a maturite (% depots), decote, retraits, penalite
D = 100;
faceDestroyed = w/(1-h);
if faceDestroyed <= Vm
  without = (w + min(D-w, Vm - faceDestroyed))/D;   % pas d'effondrement : patients au prorata
else
  without = (Vm*(1-h))/D;                           % effondrement : tout liquide, prorata general
end
withL = min(1, max(0, (Vm - w*PEN)/D));             % avec preteur : pas de vente forcee

figure;
bar([without withL]*100, 'FaceColor', [0.30 0.50 0.72]);
set(gca, 'XTickLabel', {'Sans preteur', 'Avec preteur'});
ylabel('Recupere par les deposants (%)'); ylim([0 110]); grid on;
title(sprintf('Solvable mais illiquide : %.0f%% sans preteur, %.0f%% avec', without*100, withL*100));

La valeur en risque (VaR)

Combien une banque peut-elle perdre sur son portefeuille, dans le pire des cas « normaux » ? La VaR (Value at Risk) répond : c'est la perte qu'on ne dépasse qu'avec une faible probabilité (par exemple 1 % du temps, soit 1 jour sur 100). Sur la courbe des rendements, c'est le seuil qui coupe la queue de gauche. Mais la VaR a deux angles morts. D'abord, elle ne dit rien de ce qui se passe au-delà : la perte moyenne quand on franchit ce seuil (l'Expected Shortfall) est encore pire. Ensuite, elle suppose une jolie courbe en cloche, alors que les vrais marchés ont des queues épaisses : les krachs arrivent bien plus souvent que la loi normale ne le prédit. Déplacez la volatilité, le niveau de confiance et l'épaisseur des queues : voyez la VaR sous-estimer le risque extrême.

Voir le code MATLAB
% Value at Risk (VaR) et Expected Shortfall, sous loi normale
mu = 0.5; sigma = 3; conf = 0.99;      % rendement moyen %, volatilite %, confiance
alpha = 1 - conf;                       % probabilite de queue
z = sqrt(2)*erfinv(2*alpha - 1);        % quantile normal (negatif), sans toolbox
VaR = -(mu + sigma*z);                  % perte seuil (positive)
phi = exp(-z^2/2)/sqrt(2*pi);
ES  = -(mu - sigma*phi/alpha);          % Expected Shortfall (perte moyenne au-dela)

x = linspace(mu-4*sigma, mu+3*sigma, 400);
fN = exp(-((x-mu)/sigma).^2/2)/(sigma*sqrt(2*pi));   % densite normale
q  = mu + sigma*z;                      % rendement au seuil de VaR

figure; hold on;
plot(x, fN, 'LineWidth', 2);
xt = x(x <= q); yt = fN(x <= q);
fill([xt fliplr(xt)], [yt zeros(size(yt))], [0.71 0.15 0.12], 'FaceAlpha', 0.22, 'EdgeColor', 'none'); % queue
plot([q q], [0 max(fN)], '--', 'LineWidth', 1.5);
xlabel('Rendement (%)'); ylabel('Densite');
title(sprintf('VaR %.0f%% = %.1f%%, ES = %.1f%%', conf*100, VaR, ES));
grid on;

Les marchés en direct

En bonus : les marchés en temps réel, pour observer le monde réel (données TradingView).