Der Random Walk mit schrumpfenden Schritten
Stellen Sie sich einen Preis vor, der sich jede Sekunde um einen zufälligen Betrag nach oben oder unten bewegt. Verkürzt man das Intervall immer weiter und verkleinert jeden Schritt, sodass die Gesamtstreuung vernünftig bleibt, ist der Grenzwert die Brownsche Bewegung W(t), ursprünglich für Pollen im Wasser eingeführt und 1900 von Bachelier zur Modellierung von Preisen übernommen. Sie ist durch drei Eigenschaften definiert: W(0) = 0; Zuwächse über disjunkte Intervalle sind unabhängig; und W(t) - W(s) ist normalverteilt mit Mittel 0 und Varianz t - s.
import numpy as np
rng = np.random.default_rng(1)
dt = 0.01
z = rng.standard_normal(5) # standard normal draws
increments = z * np.sqrt(dt) # each step over dt has standard deviation sqrt(dt)
print(np.round(increments, 4))Ein Pfad ist eine laufende Summe
Um einen Pfad auf einem Zeitgitter 0, dt, 2 dt, ... zu simulieren, zieht man pro Schritt ein standardnormales z, skaliert es mit sqrt(dt) und summiert: W(k * dt) ist die Summe der ersten k Zuwächse, np.cumsum. Vorn kommt eine 0, weil der Pfad bei 0 startet. Die Varianz von W(t) ist t, die Streuung der Position wächst also wie die Wurzel der Zeit, dasselbe Wurzelgesetz wie bei der Skalierung von Volatilität und VaR.
import numpy as np
def brownian_path(z, dt):
return np.concatenate([[0.0], np.cumsum(z * np.sqrt(dt))])
rng = np.random.default_rng(1)
n, dt = 252, 1 / 252
ends = np.array([brownian_path(rng.standard_normal(n), dt)[-1] for _ in range(4000)])
print(round(float(ends.mean()), 3), round(float(ends.var()), 3)) # about 0 and 1: W(1) is a standard normalEin unendlich rauer Pfad
Ein Brownscher Pfad ist stetig, aber nirgends glatt, und seine Länge ist unendlich. Seine Rauheit hat ein präzises Maß, die quadratische Variation, die Summe der quadrierten Schritte. Bei einer glatten Kurve schrumpft diese Summe mit feinerem Gitter gegen 0; bei der Brownschen Bewegung bleibt sie bei der verstrichenen Zeit t, egal wie fein das Gitter ist, denn jeder quadrierte Schritt ist etwa dt, und es gibt t / dt davon. Diese Tatsache, (dW)^2 = dt, unterscheidet die stochastische Analysis von der gewöhnlichen und ist der Schlüssel zu den nächsten Themen.
import numpy as np
def quadratic_variation(path):
return float(np.sum(np.diff(path) ** 2))
rng = np.random.default_rng(2)
t = 2.0
for steps in (10, 100, 10000):
dt = t / steps
path = np.concatenate([[0.0], np.cumsum(rng.standard_normal(steps) * np.sqrt(dt))])
print(steps, round(quadratic_variation(path), 3)) # settles near 2.0 as the grid gets finer
smooth = np.linspace(0, 1, 10001) * 2
print(round(quadratic_variation(smooth), 5)) # a straight line: close to 0Drift und Volatilität
Ein Preis hat einen Trend und eine Größenordnung. Die arithmetische Brownsche Bewegung mit Drift ist X(t) = mu * t + sigma * W(t): mu ist der Drift (der Trend pro Zeiteinheit), sigma die Volatilität (die Größenordnung des Zufallsteils). Sie ist das einfachste Modell einer Preisänderung und kann negativ werden, weshalb Preise selbst im nächsten Thema als geometrische Brownsche Bewegung modelliert werden. Sie bleibt der Baustein für Zinsen und Spreads.
import numpy as np
def drifted_path(z, dt, mu, sigma):
t = np.arange(len(z) + 1) * dt
w = np.concatenate([[0.0], np.cumsum(z * np.sqrt(dt))])
return mu * t + sigma * w
rng = np.random.default_rng(3)
n, dt = 252, 1 / 252
path = drifted_path(rng.standard_normal(n), dt, 0.08, 0.2) # 8% a year drift, 20% volatility
print(round(float(path[-1]), 4), "after one year; the drift alone would give 0.08")
print(np.round(drifted_path(np.zeros(4), 0.25, 0.08, 0.2), 4)) # no noise: just the trend linenp.random.default_rng(seed)), was einen Lauf reproduzierbar macht. Ein einzelner Pfad beweist nichts: Kennzahlen wie Mittel oder Varianz von W(1) zeigen sich erst über Tausende Pfade, und der Fehler einer Monte-Carlo-Schätzung sinkt wie 1 / sqrt(paths).- Die Brownsche Bewegung startet bei 0 und hat unabhängige normale Zuwächse der Varianz
dt: simulieren mitz * sqrt(dt)und kumulativer Summe. - Die Varianz von
W(t)istt, und die quadratische Variation eines Pfads bleibt bei der verstrichenen Zeit:(dW)^2 = dt. - Fügen Sie Trend und Größenordnung mit
X(t) = mu * t + sigma * W(t)hinzu; ein Pfad beweist nichts, Statistiken brauchen viele.
Als Nächstes: die geometrische Brownsche Bewegung, das Modell, in dem Preise nicht negativ werden können.
Lab: Was bewertet wird
- Mit
brownian_incrementsdie Schocks skalieren25 Pkt. - Mit
brownian_pathden Pfad aufbauen25 Pkt. - Mit
quadratic_variationdie Rauheit messen25 Pkt. - Mit
drifted_patheinen Trend hinzufügen25 Pkt.