public override void Process(IPathBlock block) { var blockBaseIx = block.GlobalPathIndex; var nTotalVec = new Vector <double>(_nTotal); for (var path = 0; path < block.NumberOfPaths; path += Vector <double> .Count) { var steps = block.GetStepsForFactor(path, _assetIndex); Span <Vector <double> > stepsFx = null; if (_fxName != null) { stepsFx = block.GetStepsForFactor(path, _fxIndex); } var pastSum = new Vector <double>(0.0); for (var p = 0; p < _dateIndexesPast.Length; p++) { pastSum += steps[_dateIndexesPast[p]] * (_fxName != null ? stepsFx[_dateIndexesPast[p]] : _one); } var spotAtExpiry = steps[_decisionDateIx] * (_fxName != null ? stepsFx[_decisionDateIx] : _one); if (VanillaModel != null && AverageRegressor == null) { var setReg = new double[Vector <double> .Count]; for (var i = 0; i < Vector <double> .Count; i++) { setReg[i] = spotAtExpiry[i] + _expiryToSettleCarry; } var avgVec = pastSum / nTotalVec; var setVec = new Vector <double>(setReg); var payoff = (_callPut == OptionType.C) ? Vector.Max(new Vector <double>(0), setVec - avgVec) : Vector.Max(new Vector <double>(0), avgVec - setVec); ConvertToSimCcyIfNeeded(block, path, payoff, _dateIndexes.Last()); var resultIx = (blockBaseIx + path) / Vector <double> .Count; _results[resultIx] = payoff * _notional; } else { var futSum = new double[Vector <double> .Count]; var setReg = new double[Vector <double> .Count]; for (var i = 0; i < Vector <double> .Count; i++) { futSum[i] = AverageRegressor == null ? 0.0 : AverageRegressor.Predict(spotAtExpiry[i]) * _nFuture; setReg[i] = SettlementRegressor.Predict(spotAtExpiry[i]); } var futVec = new Vector <double>(futSum); var avgVec = (futVec + pastSum) / nTotalVec; var setVec = new Vector <double>(setReg); var payoff = (_callPut == OptionType.C) ? Vector.Max(new Vector <double>(0), setVec - avgVec) : Vector.Max(new Vector <double>(0), avgVec - setVec); ConvertToSimCcyIfNeeded(block, path, payoff, _dateIndexes.Last()); var resultIx = (blockBaseIx + path) / Vector <double> .Count; _results[resultIx] = payoff * _notional; } } }
public void Process(IPathBlock block) { var blockBaseIx = block.GlobalPathIndex; var nTotalVec = new Vector <double> [_nTotal.Length]; for (var i = 0; i < nTotalVec.Length; i++) { nTotalVec[i] = new Vector <double>(_nTotal[i]); } for (var path = 0; path < block.NumberOfPaths; path += Vector <double> .Count) { var steps = block.GetStepsForFactor(path, _assetIndex); Span <Vector <double> > stepsFx = null; if (_fxName != null) { stepsFx = block.GetStepsForFactor(path, _fxIndex); } var avgs = new Vector <double> [_dateIndexes.Count]; var avgVec = new Vector <double>((_callPut == OptionType.C) ? double.MaxValue : double.MinValue); var setReg = new double[Vector <double> .Count]; for (var a = 0; a < _dateIndexes.Count; a++) { var pastSum = new Vector <double>(0.0); for (var p = 0; p < _dateIndexesPast[a].Length; p++) { pastSum += steps[_dateIndexesPast[a][p]] * (_fxName != null ? stepsFx[_dateIndexesPast[a][p]] : _one); } var spotAtExpiry = steps[_decisionDateIx] * (_fxName != null ? stepsFx[_decisionDateIx] : _one); if (VanillaModel != null && AverageRegressors[a] == null) { avgs[a] = pastSum / nTotalVec[a]; for (var i = 0; i < Vector <double> .Count; i++) { setReg[i] = spotAtExpiry[i] * _expiryToSettleCarry; } } else { var futSum = new double[Vector <double> .Count]; for (var i = 0; i < Vector <double> .Count; i++) { futSum[i] = AverageRegressors[a] == null ? 0.0 : AverageRegressors[a].Predict(spotAtExpiry[i]) * _nFuture[a]; setReg[i] = SettlementRegressor.Predict(spotAtExpiry[i]); } var futVec = new Vector <double>(futSum); avgs[a] = (futVec + pastSum) / nTotalVec[a]; } avgVec = (_callPut == OptionType.C) ? Vector.Min(avgs[a], avgVec) : Vector.Max(avgs[a], avgVec); } var setVec = new Vector <double>(setReg); var payoff = (_callPut == OptionType.C) ? Vector.Max(new Vector <double>(0), setVec - avgVec) : Vector.Max(new Vector <double>(0), avgVec - setVec); var resultIx = (blockBaseIx + path) / Vector <double> .Count; _results[resultIx] = payoff * _notional; } }