Server now returns the results of the Monte Carlo Price
This commit is contained in:
95
models.go
95
models.go
@@ -1,48 +1,33 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"math"
|
||||
"math/rand"
|
||||
"time"
|
||||
)
|
||||
|
||||
// RFC8601Time is a time.Time wrapper
|
||||
type RFC8601Time struct {
|
||||
time.Time
|
||||
}
|
||||
|
||||
func (t RFC8601Time) Sub(u RFC8601Time) time.Duration {
|
||||
return t.Sub(u)
|
||||
}
|
||||
|
||||
func (t RFC8601Time) MarshalJSON() ([]byte, error) {
|
||||
fmt.Println("Here!")
|
||||
stamp := fmt.Sprintf("\"%s\"", t.Format("2006-01-02"))
|
||||
return []byte(stamp), nil
|
||||
}
|
||||
|
||||
// Option struct that holds all the details of an option
|
||||
// Option details
|
||||
type Option struct {
|
||||
OptType int64
|
||||
Strike float64
|
||||
ExpiryDate RFC8601Time
|
||||
ExpiryDate time.Time
|
||||
|
||||
// Market data
|
||||
ValueDate RFC8601Time
|
||||
ValueDate time.Time
|
||||
Spot float64
|
||||
Rfr float64
|
||||
Vol float64
|
||||
Sims int64
|
||||
|
||||
// Results
|
||||
FV float64
|
||||
Delta float64
|
||||
Vega float64
|
||||
Rho float64
|
||||
Gamma float64
|
||||
Theta float64
|
||||
FV float64
|
||||
Delta float64
|
||||
Vega float64
|
||||
Rho float64
|
||||
Gamma float64
|
||||
Theta float64
|
||||
Levels []float64
|
||||
}
|
||||
|
||||
// Single simulation of Geometric Brownian Motion
|
||||
@@ -54,23 +39,23 @@ func gbmSimulation(spot float64, rfr float64, vol float64, tte float64, randNum
|
||||
return spot * math.Exp(drift+stoch)
|
||||
}
|
||||
|
||||
// RunSimulations is the main function that runs Monte Carlo simulations
|
||||
// runSimulations is the main function that runs Monte Carlo simulations
|
||||
// for an option. Note that it runs normal Geometric Brownian Motion
|
||||
// to calculate the future spot levels
|
||||
func RunSimulations(opt *Option) {
|
||||
func runSimulations(opt *Option) {
|
||||
|
||||
var i int64
|
||||
var level float64
|
||||
|
||||
levels := make([]float64, opt.Sims)
|
||||
opt.Levels = make([]float64, opt.Sims)
|
||||
|
||||
tte := opt.ExpiryDate.Sub(opt.ValueDate).Hours() / (24 * 365)
|
||||
|
||||
for i = 0; i < opt.Sims; i++ {
|
||||
randNum := rand.NormFloat64()
|
||||
// Base
|
||||
levels[i] = gbmSimulation(opt.Spot, opt.Rfr, opt.Vol, tte, randNum)
|
||||
opt.FV += math.Max((levels[i]-opt.Strike)*float64(opt.OptType), 0)
|
||||
opt.Levels[i] = gbmSimulation(opt.Spot, opt.Rfr, opt.Vol, tte, randNum)
|
||||
opt.FV += math.Max((opt.Levels[i]-opt.Strike)*float64(opt.OptType), 0)
|
||||
|
||||
// Delta
|
||||
level = gbmSimulation(opt.Spot+0.0001, opt.Rfr, opt.Vol, tte, randNum)
|
||||
@@ -104,52 +89,8 @@ func RunSimulations(opt *Option) {
|
||||
opt.Rho = (opt.Rho/float64(opt.Sims)*math.Exp(-(opt.Rfr+0.01)*tte) - opt.FV)
|
||||
}
|
||||
|
||||
/*
|
||||
func main() {
|
||||
value := time.Date(2016, 12, 30, 0, 0, 0, 0, time.UTC)
|
||||
expiry := time.Date(2017, 12, 30, 0, 0, 0, 0, time.UTC)
|
||||
opt := Option{optType: 1, strike: 100, expiryDate: expiry, valueDate: value, spot: 100, rfr: 0.03, vol: 0.25, sims: 1000000}
|
||||
rand.Seed(time.Now().UTC().UnixNano())
|
||||
RunSimulations(&opt)
|
||||
|
||||
fmt.Printf(
|
||||
`
|
||||
Valuation date: %s
|
||||
|
||||
|
||||
| BS Analytic | BS Monte Carlo |
|
||||
---------------------------------------------
|
||||
|Type: | %10s | %13s |
|
||||
|Spot: | %10.2f | %13.2f |
|
||||
|Expiry: | %s | %s |
|
||||
|Strike: | %10.2f | %13.2f |
|
||||
|Risk-free: | %10.2f%% | %13.2f%% |
|
||||
|Implied Vol:| %10.2f%% | %13.2f%% |
|
||||
---------------------------------------------
|
||||
|Fair value: | %8.4f | %11.4f |
|
||||
|Delta: | %8.4f | %11.4f |
|
||||
|Gamma: | %8.4f | %11.4f |
|
||||
|Vega: | %8.4f | %11.4f |
|
||||
|Theta: | %8.4f | %11.4f |
|
||||
|Rho: | %8.4f | %11.4f |
|
||||
|Simulations:| | %11d |
|
||||
---------------------------------------------
|
||||
|
||||
`,
|
||||
value.Format("2006-01-02"),
|
||||
"Call", "Call",
|
||||
opt.Spot, opt.Spot,
|
||||
expiry.Format("2006-01-02"), expiry.Format("2006-01-02"),
|
||||
opt.Strike, opt.Strike,
|
||||
opt.Rfr*100, opt.Rfr*100,
|
||||
opt.Vol*100, opt.Vol*100,
|
||||
opt.FV, opt.FV,
|
||||
opt.Delta, opt.Delta,
|
||||
opt.Gamma, opt.Gamma,
|
||||
opt.Vega, opt.Vega,
|
||||
opt.Theta, opt.Theta,
|
||||
opt.Rho, opt.Rho,
|
||||
opt.Sims)
|
||||
|
||||
// PriceMonteCarlo is the exported method to run the simulations and value
|
||||
// a vanilla option using Monte Carlo methods
|
||||
func (opt *Option) PriceMonteCarlo() {
|
||||
runSimulations(opt)
|
||||
}
|
||||
*/
|
||||
|
||||
Reference in New Issue
Block a user