public override Report Run(Dictionary <string, Dictionary <DateTime, ITradingData> > portfolioDataset, List <DateTime> tradingCalendar, BacktestingProperty property, Dictionary <string, PortfolioSubject> portfolio, Period period, bool isBenchmark = false) { _simulator = new Simulator(); return(_simulator.Run(this, portfolioDataset, tradingCalendar, property, portfolio, period, isBenchmark)); }
public Report Run(StrategyBase strategy, Dictionary <string, Dictionary <DateTime, ITradingData> > portfolioDataset, List <DateTime> tradingCalendar, BacktestingProperty property, Dictionary <string, PortfolioSubject> portfolio, Period period, bool isBenchmark = false) { _strategy = strategy; _isBenchmark = isBenchmark; _report = new Report(_strategy.StrategyType); _portfolioDataset = portfolioDataset; _tradingCalendar = tradingCalendar; _portfolio = portfolio; Property = property; _balance = property.Capital; _highestTotalBalance = property.Capital; foreach (var assetCode in _portfolioDataset.Keys) { var initialBalance = Property.Capital * _portfolio[assetCode].Ratio; _holdStocks.Add(assetCode, new HoldStock { InitialBalance = initialBalance }); _report.Transactions.Add(assetCode, new Dictionary <DateTime, List <Transaction> >()); // 에셋별로 실제거래한 날짜데이터를 갖는다(트레이딩 달력이랑 다름) var tradingDate = portfolioDataset[assetCode].Keys.ToList(); _tradingDates.Add(assetCode, tradingDate); _tradingIndex.Add(assetCode, 0); _recordDetails.Add(assetCode, new List <RecordDetail>()); } foreach (var date in tradingCalendar) { _currentDate = date; // 트레이딩 달력기준 날짜 _totalBalanceSnapshot = _report.Records.Count > 0 ? _report.Records.Last().TotalBalance : _balance; var recordDetails = new List <RecordDetail>(); foreach (var assetCode in _portfolioDataset.Keys) { var subjectDataset = _portfolioDataset[assetCode]; if (subjectDataset.ContainsKey(date)) { _strategy.OnAfterOpen(assetCode); var recordDetail = CreateRecordDetail(assetCode); _recordDetails[assetCode].Add(recordDetail); recordDetails.Add(recordDetail); _tradingIndex[assetCode]++; } else { // var prevRecord = _report.Records.OrderByDescending(x => x.Date).Take(1).FirstOrDefault(); var prevRecordDetail = _recordDetails[assetCode].OrderByDescending(x => x.Date).Take(1).FirstOrDefault(); if (prevRecordDetail != null) { var recordDetail = new RecordDetail() { Date = _currentDate, AssetCode = assetCode, RatingBalance = prevRecordDetail.RatingBalance, Return = 0, ReturnRatio = 0, CumulativeReturn = prevRecordDetail.CumulativeReturn }; _recordDetails[assetCode].Add(recordDetail); recordDetails.Add(recordDetail); } } } var record = CreateRecord(date, recordDetails); _report.Records.Add(record); if (IsFirstTradingDateOfYear(_currentDate.Year)) { _balanceOfYears.Add(_currentDate.Year, new BalanceOfPeriod { FirstDateBalance = _report.Records.Last().TotalBalance }); } else if (IsLastTradingDateOfYear(_currentDate.Year)) { _balanceOfYears[_currentDate.Year].LastDateBalance = _report.Records.Last().TotalBalance; } if (IsFirstTradingDateOfMonth(_currentDate.Year, _currentDate.Month)) { _balanceOfMonths.Add(_currentDate.ToString("yyyy-MM"), new BalanceOfPeriod { FirstDateBalance = _report.Records.Last().TotalBalance }); } else if (IsLastTradingDateOfMonth(_currentDate.Year, _currentDate.Month)) { _balanceOfMonths[_currentDate.ToString("yyyy-MM")].LastDateBalance = _report.Records.Last().TotalBalance; } } // 통계생성 string relationalKey = Guid.NewGuid().ToString(); var summaryDetails = CreateSummaryDetails(relationalKey); _report.Summary = CreateSummary(summaryDetails, relationalKey); _report.AnnualReturns = CreateAnnualReturns(); _report.MonthlyReturns = CreateMonthlyReturns(); return(_report); }
public abstract Report Run(Dictionary <string, Dictionary <DateTime, ITradingData> > portfolioDataset, List <DateTime> tradingCalendar, BacktestingProperty property, Dictionary <string, PortfolioSubject> portfolio, Period period, bool isBenchmark = false);