private String m_strPriceFldName = "fClose"; // Name of used prices column #endregion Data members #region Constructors, Initialization & Destructor public cImportedPort(IPortfolioBL cPort) { m_objPortfolio = cPort; m_objErrorHandler = m_objPortfolio.cErrorLog; //m_colSecurities = new cSecurities(m_objPortfolio); //m_dtDate = DateTime.Now; m_drDateRange = new cDateRange(DateTime.Now.AddYears(-2), DateTime.Now); }//constructor
}//getPerioTotalRates public static Boolean isBelowNumberOfMonths(cDateRange drPeriod, int iMonths) { if (((drPeriod.EndDate - drPeriod.StartDate).Days / 30) <= iMonths) { return(true); } return(false); } //isBelowNumberOfMonths
}//getClassicRateValue public static double getFinalReturnValue(List <PriceReturn> dtMain, cDateRange drPeriod) { // Returns final return value for period /// New Formula: multiply by specific coefficient for each year if ((dtMain == null) || (dtMain.Count == 0)) { return(0D); } // Calculate each year return List <double> yearlyReturns = getSeperateYearsReturns(dtMain, drPeriod); // Calculate final return int iNbWeeks = 0; double zVal = 0D; double dFinalVal = 0D; if (dtMain.Count > 105) { // Above 2 years (CASES 1 + 2) dFinalVal = (1 + yearlyReturns[0] * 0.4D) * (1 + yearlyReturns[1] * 0.24D) * (1 + yearlyReturns[2] * 0.15D) - 1; } else { if ((dtMain.Count == 104) || (dtMain.Count == 105)) { // Exactly 2 years (CASE 3) dFinalVal = (1 + yearlyReturns[0] * 0.53D) * (1 + yearlyReturns[1] * 0.31D) - 1; } else { if (dtMain.Count > 52) { // Between 1 & 2 years (CASE 4) iNbWeeks = dtMain.Count - 52; zVal = (double)(104 - iNbWeeks) / 52D; dFinalVal = (1 + yearlyReturns[0] * 0.53D * zVal) * (1 + yearlyReturns[1] * 0.31D * ((double)iNbWeeks / 52D)) - 1; } else { if (dtMain.Count == 52) { // Exactly 1 year (CASE 5) dFinalVal = yearlyReturns[0]; } else { if (dtMain.Count < 52) { // Below 1 year (CASE 6) dFinalVal = yearlyReturns[0] * (52D / (double)dtMain.Count); } } } } } return(dFinalVal); }//getFinalReturnValue
}//getDataTblFldStDev public static double getAnnualizedValue(double dOrigVal, cDateRange cDrPrices) { // Retrieves the annualized version int iDays = cDrPrices.EndDate.Subtract(cDrPrices.StartDate).Duration().Days + 1; double dPower = (iDays > 365) ? 365D / iDays : iDays / 365D; double dFinal = Math.Pow(Math.Abs(dOrigVal + 1), dPower) - 1; // Annualization return(dFinal); }//getAnnualizedValue
}//constructor #endregion Consturctors, Initialization & Destructor #region Methods #region General methods public void setBacktestingSecuritiesCollection(ISecurities secsCol, cDateRange cDrRange) { // Sets the collection of backtesting securities, based on a given securities collection m_colSecurities = secsCol; m_colBackSecurities.Clear(); for (int iSecs = 0; iSecs < secsCol.Count; iSecs++) { m_colBackSecurities.Add(new cBacktestingSecurity(m_objPortfolio, secsCol[iSecs], cDrRange)); } }//setBacktestingSecuritiesCollection
private Boolean m_isDisabled = false; // Whether the system has disabled the current security #endregion Data members #region Consturctors, Initialization & Destructor public cBacktestingSecurity(IPortfolioBL cPort, ISecurity cSec, cDateRange Dates) { m_objPortfolio = cPort; m_objErrorHandler = m_objPortfolio.cErrorLog; m_objColHandler = m_objPortfolio.ColHandler; m_objSecurity = cSec; m_drDateRange = Dates; try { } catch (Exception ex) { m_objErrorHandler.LogInfo(ex); } }//cSecurity constructor
}//constructor #endregion Constructors, Initialization & Destructor #region Methods public void setSecurityPrices(cDateRange cDrPort) { // Sets the prices of the securities relevant for the portfolio date range if (m_objCurrSec == null) { return; } try { m_dStartPrice = getSecurityPrice(cDrPort.StartDate); m_dEndDate = getSecurityPrice(cDrPort.EndDate); } catch (Exception ex) { m_objErrorHandler.LogInfo(ex); } }//setSecurityPrices
}//cSecurity constructor #endregion Consturctors, Initialization & Destructor #region Methods #region Base methods public void Init(IPortfolioBL cPort) { m_objPortfolio = cPort; m_objErrorHandler = m_objPortfolio.cErrorLog; m_objColHandler = m_objPortfolio.ColHandler; m_objSecAnalytics = new cSecAnalytics(this, m_objErrorHandler, m_objColHandler); m_objPrices.Portfolio = cPort; try { //LR: why do we have 5 years of date range here ??? m_sPricesRange = new cDateRange(DateTime.Today.AddYears(-cProperties.DatesInterval).AddDays(-1), DateTime.Today.AddDays(-1)); m_objRates = new cRateData(this, m_objPortfolio, false); m_objCovarData = new cCovarCorrelData(this, m_objColHandler, m_objErrorHandler, true); m_objCorrelData = new cCovarCorrelData(this, m_objColHandler, m_objErrorHandler, false); } catch (Exception ex) { m_objErrorHandler.LogInfo(ex); } }
private List <double> m_colVolumes = new List <double>(); // Collection of traded volumes for each day in full date-range #endregion Data members #region Consturctors, Initialization & Destructor public cSecurity(IPortfolioBL cPort, string secName, string secSymbol) { m_objPortfolio = cPort; m_objErrorHandler = m_objPortfolio.cErrorLog; m_objColHandler = m_objPortfolio.ColHandler; m_objSecProperties = new cSecProperties(m_objErrorHandler, m_objPortfolio); m_objSecAnalytics = new cSecAnalytics(this, m_objErrorHandler, m_objColHandler); m_objSecProperties.SecurityName = m_objSecProperties.getSecName(secName); // No ' signs + trim spaces m_objSecProperties.SecuritySymbol = secSymbol; m_objSecProperties.SecColor = System.Drawing.Color.FromArgb(cProperties.RndGenerator.Next(255), cProperties.RndGenerator.Next(255), cProperties.RndGenerator.Next(255)); m_objPrices = new cPriceData(this, m_objPortfolio); try { m_sPricesRange = new cDateRange(DateTime.Today.AddYears(-cProperties.DatesInterval).AddDays(-1), DateTime.Today.AddDays(-1)); m_objRates = new cRateData(this, m_objPortfolio, false); m_objCovarData = new cCovarCorrelData(this, m_objColHandler, m_objErrorHandler, true); m_objCorrelData = new cCovarCorrelData(this, m_objColHandler, m_objErrorHandler, false); } catch (Exception ex) { m_objErrorHandler.LogInfo(ex); } }//cSecurity constructor
}//clearCalcData #endregion Constructors, Initialization & Destructor #region Methods #region New methods public double[,] calcRiskAndCovariance(cDateRange drPeriod, ref ISecurities cSecsCol, Boolean isMatrix, Boolean isBacktest) { // Runs the main covariance calculation (including covariance matrix) /// The matrix's first dimension represents the variables (securities)C:\Users\uriel\Documents\Applications\Cherries\Classes\ /// The matrix's second dimension represents the observations (history) try { if (isBacktest) { for (int iSer = 0; iSer < cSecsCol.Count; iSer++) { cSecsCol[iSer].RatesClass.setUpdatedRateData(drPeriod); } } else { for (int iSer = 0; iSer < cSecsCol.Count; iSer++) { cSecsCol[iSer].RatesClass.setFinalReturnFromServer(drPeriod); } } cSecsCol = cSecsCol.getListOfActiveSecs(); for (int iSecs = 0; iSecs < cSecsCol.Count; iSecs++) { cSecsCol[iSecs].CovarClass.setCalculationStatistics(isBacktest); } cSecsCol = cSecsCol.getListOfActiveSecs(); if (isMatrix) { calculateNewCovarianceMatrix(cSecsCol, isBacktest); } } catch (Exception ex) { m_objErrorHandler.LogInfo(ex); } return(m_dCovarMatrix); }//runMainCalculation
}//initMainVars #endregion Constructors, Initialization & Destructor #region Methods #region Calculation methods public OptimalPortoliosViewModel calculateNewEfficientFrontier(ref ISecurities cSecsCol, ISecurities cBenchmarksCol, cDateRange drCalcRange, Boolean isClearDisabled, Boolean isBacktest) { // Calculates the Efficient Frontier including the rates vector and covariance matrix /// Parameters: cSecsCol - collection of securities for optimization /// drCalcRange - date range for calculation OptimalPortoliosViewModel vmOptimal = new OptimalPortoliosViewModel(); try { //m_colSecurities = cSecsCol; if (cSecsCol.Count > 0) { // Data exists for calculations if (isClearDisabled) { m_objColHandler.DisabledSecs.Clear(); } // Calculate covariance m_objPortfolio.Classes.CovarCorrel.calcRiskAndCovariance(drCalcRange, ref cBenchmarksCol, false, isBacktest); m_arrCovarData = m_objPortfolio.Classes.CovarCorrel.calcRiskAndCovariance(drCalcRange, ref cSecsCol, true, isBacktest); //m_colSecurities = cSecsCol; // Calculate optimal portfolios runEfficientFrontierModule(cSecsCol); setStartingRiskLevel(); setSecuritiesQuantities(cSecsCol); setSecuritiesDatatable(cSecsCol); // In case of Backtesting there is no need to call this function //m_objCovarCalcs.reportCovarianceMatrix(cSecsCol, m_dtSecsData, Portfolios[PortNumA], m_objPortfolio.Details.Equity, isBacktest); //m_objCovarCalcs.reportCovarianceMatrix(cSecsCol, m_dtSecsData, Portfolios[0], m_objPortfolio.Details.Equity, isBacktest); } } catch (Exception ex) { m_objErrorHandler.LogInfo(ex); } setCalcSuccess(); if (!m_isSuccessfulCalc) { vmOptimal.Messages.Add(new Models.App.Message { Text = "Failed to calculate due to: " + m_strEngineErrors, LogLevel = Models.App.LogLevel.Fatal }); } else { vmOptimal = AutoMapper.Mapper.Map <OptimalPortoliosViewModel>(m_objPortfolio.Classes.Optimizer); vmOptimal.PortID = m_objPortfolio.Details.ID; vmOptimal.PortDetails = m_objPortfolio.Details; for (int iPorts = 0; iPorts < vmOptimal.Portfolios.Count; iPorts++) { for (int iSecs = 0; iSecs < vmOptimal.Portfolios[iPorts].Securities.Count; iSecs++) { // Securities displayed on page vmOptimal.Portfolios[iPorts].Securities[iSecs].StdYield *= Math.Sqrt(52); vmOptimal.Portfolios[iPorts].Securities[iSecs].FinalRate *= 52; //vmOptimal.PortNumA vmOptimal.Portfolios[iPorts].Securities[iSecs].StandardDeviation *= 1; } } } return(vmOptimal); }//calculateNewEfficientFrontier
}//clearCalcData #endregion Consturctors, Initialization & Destructor #region Methods #region Global datatable //public void setPortfolioPricesFromDB() //{ // Loads the prices relevant to the current portfolio // try // { // ArrayList param = new ArrayList(); // cDateRange drPeriod = new cDateRange(DateTime.Today.AddYears(-cProperties.DatesInterval), DateTime.Today.AddDays(-1)); // for (int iSecs = 0; iSecs < m_objColHandler.Securities.Count; iSecs++) // { // Loads all securities // // Set adjusted price // cBasicStaticCalcs.calcAdj(m_objColHandler.Securities[iSecs].PriceTable, DateTime.Today.AddDays(-1).DayOfWeek, m_objColHandler.Securities[iSecs]); // //cBasicStaticCalcs.setAccumulatedCoefficientsForSecurity(m_objColHandler.Securities[iSecs].PriceTable); // //cBasicStaticCalcs.calculateAdjustedPrices(m_objColHandler.Securities[iSecs].PriceTable, drPeriod); // } // } // catch (Exception ex) // { // m_objErrorHandler.LogInfo(ex); // } //}//setPortfolioPricesFromDB public List <Rate> GetPrices(string secId, string currency) { // Retrieves prices for securities List <cSecurity> lst; List <Price> lstPrices = null; List <Rate> rates = new List <Rate>(); if (StaticData <cSecurity, ISecurities> .lst == null) { lst = new List <cSecurity>(); } else { lst = StaticData <cSecurity, ISecurities> .lst; } var sec = lst.FirstOrDefault(x => x.Properties.PortSecurityId == secId); if (sec != null) { lstPrices = sec.PriceTable; } else { _repository.Execute(session => { lstPrices = session.Query <Price>().Where(x => x.idSecurity == secId).OrderByDescending(x => x.dDate).ToList(); }); } double price; Double basePriceforReturnCalc; Double currPriceforReturnCalc; cDateRange drCalc = new cDateRange(DateTime.Today.AddYears(-cProperties.DatesInterval), DateTime.Today.AddDays(-1)); Double returnVaue = 0; DateTime baseDTforReturnCalc = lstPrices.Last().dDate; //TODO:CHECK FOR CURRENCY and take fcloseNIS basePriceforReturnCalc = lstPrices.Last().fClose.HasValue&& lstPrices.Last().fClose > 0 ? lstPrices.Last().fClose.Value : lstPrices.Last().fClose.Value; int years = 0; int yearsSaved = 0; DateTime lastDT = lstPrices[0].dDate; while ((baseDTforReturnCalc.AddDays(-1)).AddYears(years) <= lastDT) { years++; } if (years > 0) { years--; yearsSaved = years; } int index = 0; for (int iRows = 0; iRows < lstPrices.Count; iRows++) { index = index + 1; // Replacing '.dAdjPrice' with 'fClose', but it should be rewriten to consider 'currency' (fNISClose) price = lstPrices[iRows].fClose.HasValue && lstPrices[iRows].fClose > 0 ? lstPrices[iRows].fClose.Value : lstPrices[iRows].fClose.Value; currPriceforReturnCalc = price; if (index == 7 || (years > 0 && (baseDTforReturnCalc.AddDays(-1)).AddYears(years).ToOADate() == lstPrices[iRows].dDate.ToOADate())) { string label = ""; if (years > 0 && (baseDTforReturnCalc.AddDays(-1)).AddYears(years).ToOADate() == lstPrices[iRows].dDate.ToOADate()) { returnVaue = (currPriceforReturnCalc / basePriceforReturnCalc - 1) * 100; label = string.Format("{0} years return:{2}{1:#,##0.00} %", (years).ToString(), returnVaue, ""); years--; } rates.Add(new Rate { Date = lstPrices[iRows].dDate, RateVal = price, Tooltip = string.Format("Date : {0:dd/MM/yy} Price: {1:#,##0.00}", lstPrices[iRows].dDate, price), Label = label }); index = 0; } } return(rates.OrderBy(o => o.Date).ToList()); }
}//getFinalReturnValue private static List <double> getSeperateYearsReturns(List <PriceReturn> dtMain, cDateRange drPeriod) { // Calculates final return for each seperate year in collection double T1 = 0D, T2 = 0D, T3 = 0D; List <PriceReturn> prStart = new List <PriceReturn>(), prEnd = new List <PriceReturn>(); List <double> colReturns = new List <double>(); // T1 prEnd.Add(dtMain[dtMain.Count - 1]); if (dtMain.Count <= 52) // Below a year { prStart.Add(dtMain[0]); } else { prStart.Add(dtMain[dtMain.Count - 53]); } //var nearestDiff = dtMain.Min(x => Math.Abs((x.dtDate.Date - prEnd[0].dtDate.AddYears(-1)).Ticks)); //prStart = dtMain.Where(x => Math.Abs((x.dtDate.Date - prEnd[0].dtDate.AddYears(-1)).Ticks) == nearestDiff).ToList(); // should find 1 row on that day T1 = ((double)prEnd[0].fAdjClose / (double)prStart[0].fAdjClosePrevWeek) - 1D; colReturns.Add(T1); // T2 if (dtMain.Count > 53) { // Second Year prEnd.Clear(); prEnd.Add(dtMain[dtMain.Count - 54]); prStart.Clear(); if (dtMain.Count <= 105) // Below 2 years { prStart.Add(dtMain[0]); } else { prStart.Add(dtMain[dtMain.Count - 106]); } //nearestDiff = dtMain.Min(x => Math.Abs((x.dtDate.Date - prEnd[0].dtDate.AddYears(-1)).Ticks)); //prStart = dtMain.Where(x => Math.Abs((x.dtDate.Date - prEnd[0].dtDate.AddYears(-1)).Ticks) == nearestDiff).ToList(); // should find 1 row on that day if (prStart.Count > 0) { T2 = ((double)prEnd[0].fAdjClose / (double)prStart[0].fAdjClosePrevWeek) - 1D; } colReturns.Add(T2); } else { colReturns.Add(0D); } // T3 if (dtMain.Count > 105) { // If a second year exists in price returns collection prEnd.Clear(); prEnd.Add(dtMain[dtMain.Count - 106]); prStart.Clear(); if (dtMain.Count < 156) // Below 2 years { prStart.Add(dtMain[0]); } else { prStart.Add(dtMain[dtMain.Count - 156]); } //nearestDiff = dtMain.Min(x => Math.Abs((x.dtDate.Date - prEnd[0].dtDate.AddYears(-1)).Ticks)); //prStart = dtMain.Where(x => Math.Abs((x.dtDate.Date - prEnd[0].dtDate.AddYears(-1)).Ticks) == nearestDiff).ToList(); // should find 1 row on that day if (prStart.Count > 0) { T3 = ((double)prEnd[0].fAdjClose / (double)prStart[0].fAdjClosePrevWeek) - 1D; } colReturns.Add(T3); } else { colReturns.Add(0D); } return(colReturns); }//getSeperateYearsReturns
public static void calculatePriceReturns(List <Entities.dbo.Price> dtPrices, ref List <Rate> dtOut, cDateRange cDrCalc, enumDateFreq enCalcFreq, String idSec, String strSymbol) { calculatePriceReturns(dtPrices, ref dtOut, cDrCalc, enCalcFreq, 0, dtPrices.Count - 1, idSec, strSymbol); } //calculatePriceReturns
}//getSeperateYearsReturns public static List <PriceReturn> getPriceReturnsInDateRange(List <PriceReturn> colReturns, cDateRange drPeriod) { // Returns a collection of price returns relevant to date range List <PriceReturn> colFinal = new List <PriceReturn>(); for (int iRows = 0; iRows < colReturns.Count; iRows++) { if ((colReturns[iRows].dtDate >= drPeriod.StartDate) && (colReturns[iRows].dtDate <= drPeriod.EndDate)) { colFinal.Add(colReturns[iRows]); } } return(colFinal); }//getPriceReturnsInDateRange
} //calculatePriceReturns public static void calculatePriceReturns(List <Entities.dbo.Price> dtPrices, ref List <Rate> dtOut, cDateRange cDrCalc, enumDateFreq enCalcFreq, int iPosStart, int iPosEnd, String idSec, String strSymbol) { // Calculates price returns for the given table of prices DateTime dtCurrent = DateTime.Now, dtNextVal; int iNextIndex = 0; for (int iRows = iPosStart; iRows <= iPosEnd;) { // Goes through prices backwards dtCurrent = dtPrices[iRows].dDate; if ((dtCurrent < cDrCalc.StartDate) || (dtCurrent > cDrCalc.EndDate)) { iRows++; continue; } // No calculations if exceeds calculation range dtNextVal = getNextDate(dtCurrent, enCalcFreq); iNextIndex = getClosestDateRowIndex(dtPrices, iRows, dtNextVal, cDrCalc); if ((iNextIndex == -1) || (iNextIndex >= iPosEnd) || ((iPosEnd - iRows) < 7)) { return; // Finished } double dRateVal = getCalcRateVal(Convert.ToDouble(dtPrices[iRows].fClose), Convert.ToDouble(dtPrices[iNextIndex].fClose)); // calculated rate dtOut.Add(new Rate { Date = dtCurrent, RateVal = dRateVal }); if (iNextIndex > iRows) { iRows = iNextIndex; } else { iRows++; } } //main for } //calculatePriceReturns
}//getCummulativeReturnValue #endregion Final rates methods #region Helping methods private static int getClosestDateRowIndex(List <Entities.dbo.Price> dtMain, int iPrevIndex, DateTime dtCompare, cDateRange cDrCalc) {//get the most nearly index to request date return -1 if no more dates in the table int iFinalRow = iPrevIndex, iMinDiff = int.MaxValue; TimeSpan tsDateDiff; DateTime dtTmp; for (int iRows = iFinalRow + 1; iRows < dtMain.Count; iRows++) { // Finds closest date row index dtTmp = dtMain[iRows].dDate; if (dtTmp >= cDrCalc.StartDate && dtTmp <= cDrCalc.EndDate) { tsDateDiff = dtCompare.Subtract(dtTmp); if (System.Math.Abs(tsDateDiff.Days) <= iMinDiff) { iFinalRow = iRows; iMinDiff = System.Math.Abs(tsDateDiff.Days); } // Marks smaller date differences else { return(iFinalRow); // Once difference is bigger - stop (we deal with a sorted table) } } } if (iFinalRow == iPrevIndex) { return(-1); } return(iFinalRow); }//getClosestDateRowIndex
}//getAdjustedPrice #endregion Price return methods #region Final rates methods public static double getClassicRateValue(List <Entities.dbo.Price> dtMain, string currencyType, cDateRange drPeriod) { // Retrieves the Final rate value for a given security double prevPrc, currPrc; List <Entities.dbo.Price> prevPrice = new List <Entities.dbo.Price>(); List <Entities.dbo.Price> currPrice = new List <Entities.dbo.Price>(); var nearestDiff = dtMain.Min(x => Math.Abs((x.dDate.Date - drPeriod.StartDate.Date).Ticks)); prevPrice = dtMain.Where(x => Math.Abs((x.dDate.Date - drPeriod.StartDate.Date).Ticks) == nearestDiff).ToList(); // should find 1 row on that day nearestDiff = dtMain.Min(x => Math.Abs((x.dDate.Date - drPeriod.EndDate.Date).Ticks)); currPrice = dtMain.Where(x => Math.Abs((x.dDate.Date - drPeriod.EndDate.Date).Ticks) == nearestDiff).ToList(); // should find 1 row on that day //prevPrice = dtMain.Where(x => x.dDate.Date == drPeriod.StartDate.Date).ToList(); // should find 1 row on that day //currPrice = dtMain.Where(x => x.dDate.Date == drPeriod.EndDate.Date).ToList(); // should find 1 row on that day if (prevPrice.Count == 0 || currPrice.Count == 0) { return(0D); } if (currencyType == "9999") { prevPrc = (double)prevPrice[0].fNISClose; currPrc = (double)currPrice[0].fNISClose; } else { prevPrc = (double)prevPrice[0].fClose; currPrc = (double)currPrice[0].fClose; } if (prevPrc == 0D) { return(0D); } return(getCalcRateVal(currPrc, prevPrc)); }//getClassicRateValue