Пример #1
0
func (self SGD) addBiasToMatrix(x mat.MatrixRO) *mat.DenseMatrix {
	xb := mat.Ones(x.Rows(), self.InputDims()+1)
	for r := 0; r < x.Rows(); r++ {
		for i := 0; i < self.InputDims(); i++ {
			xb.Set(r, i, x.Get(r, i))
		}
	}
	return xb
}
// generateReturns generates performance specifically for assets, and returns
// separately by asset class as a map
// Receiver: SimulationData
// Params: numberOfMonths int -- number of periods to model
// Returns: returnResultsByAsset
func (s *SimulationData) generateReturns(numberOfMonths int) returnResultsByAsset {
	assetPerformanceData := s.AssetPerformanceData // map[string]Distribution
	assetClassIds := s.assetClassIds()             // []string
	numberOfAssets := len(assetClassIds)

	choleskyApplied := s.applyCholeskyDecomposition(numberOfMonths)

	prices := goMatrix.Zeros(numberOfMonths, numberOfAssets)

	for row := 0; row < prices.Rows(); row++ {
		for column := 0; column < prices.Cols(); column++ {
			var startingValue float64
			if row == 0 {
				startingValue = 0.0
			} else {
				startingValue = prices.Get((row - 1), column)
			}

			assetId := assetClassIds[column] // These are sorted alphabetically
			assetStats := assetPerformanceData[assetId]
			assetMeanReturn := assetStats.Mean
			assetStdDev := assetStats.StdDev

			b := assetMeanReturn - 0.5*math.Pow(assetStdDev, 2)
			c := assetStdDev * choleskyApplied.Get(row, column)

			// Can't do the exp(x) in the same step as you need to use the previous value as a starting price!
			prices.Set(row, column, (startingValue + b + c))
		}

	}

	for row := 0; row < prices.Rows(); row++ {
		for column := 0; column < prices.Cols(); column++ {
			basePrice := prices.Get(row, column)
			expPrice := math.Exp(basePrice)
			prices.Set(row, column, expPrice)
		}
	}

	/* Convert prices to relative returns. */
	// Add T=0, price=1.0
	initialPrices := goMatrix.Ones(1, numberOfAssets)
	augmentedPrices, _ := initialPrices.Stack(prices)

	// Create base matrix
	asRelativeReturns := goMatrix.Zeros(numberOfMonths, numberOfAssets)

	// Each row in the prices matrix is a list of asset prices in each year - NOT
	// the progression of a single asset. We'll need to grab columns for that.
	for column := 0; column < augmentedPrices.Cols(); column++ {
		priceValues := augmentedPrices.GetColVector(column).Array() // []float64
		for periodIndex, periodPrice := range priceValues {
			if periodIndex == 0 {
				// Nothing to do on the first column
				continue
			}
			lastPrice := priceValues[periodIndex-1]
			pctReturn := (periodPrice - lastPrice) / lastPrice
			asRelativeReturns.Set((periodIndex - 1), column, pctReturn)
		}
	}
	/* */

	results := asRelativeReturns.Arrays()    // [][]float64
	resultsByAsset := returnResultsByAsset{} // map[string][]float64
	for _, assetClassId := range assetClassIds {
		resultsByAsset[assetClassId] = make([]float64, numberOfMonths)
	}

	for periodIndex, resultSet := range results {
		for assetIndex, returnResult := range resultSet {
			assetClassId := assetClassIds[assetIndex]
			resultsByAsset[assetClassId][periodIndex] = returnResult
		}
	}

	return resultsByAsset
}