public void Rebalance(List <Symbol> symbols, Rebalancing reb, DateTime currentDate) { logger.Info($"{currentDate} START REBALANCING"); decimal money = CurrentMoney + GetPortfolioValue(currentDate); logger.Debug("Total account value " + money); decimal moneyForEachSymbol = money / 100 * reb.MaxPercentForShare; // There is a rebalancing issue, when we have to sell some stocks but can't because of big lot or share price logger.Debug("Money for each symbol " + moneyForEachSymbol); //sell cycle foreach (Symbol symbol in symbols) { logger.Debug("Sell balancing cycle for " + symbol.Code); var symbolQuote = symbol.GetDailyQuote(currentDate); long quantity = Portfolio.getQuantity(symbol); decimal sharesCost = quantity * symbolQuote.Open; logger.Debug($"Cost of {symbol.Code}: " + sharesCost); var moneyForTrade = (long)(moneyForEachSymbol - sharesCost); logger.Debug("Money for trade: " + moneyForTrade); if (moneyForTrade < 0 && moneyForTrade < symbolQuote.Open) { logger.Debug("Current cash: " + GetCurrentMoneyFormatted()); Operation oper = Sell(symbol, Math.Abs(moneyForTrade), currentDate); if (oper != null) { oper.isRebalanced = true; } logger.Debug("Current cash: " + GetCurrentMoneyFormatted()); } else { logger.Info($"No needed to Sell {symbol.Code}"); } } //buy cycle foreach (Symbol symbol in symbols) { logger.Debug("Buy balancing cycle for " + symbol.Code); var symbolQuote = symbol.GetDailyQuote(currentDate); long quantity = Portfolio.getQuantity(symbol); decimal sharesCost = quantity * symbolQuote.Open; logger.Debug($"Cost of {symbol.Code}: " + sharesCost); decimal moneyForTrade = moneyForEachSymbol - sharesCost; logger.Debug("Money for trade: " + moneyForTrade); if (moneyForTrade > 0) { if (moneyForTrade > CurrentMoney) { moneyForEachSymbol = moneyForEachSymbol - (moneyForTrade - CurrentMoney); // There is a rebalancing issue, when we have to sell some stocks but can't because of big lot or share price moneyForTrade = moneyForTrade - (moneyForTrade - CurrentMoney); } logger.Debug("Current cash: " + GetCurrentMoneyFormatted()); Operation operation = Buy(symbol, moneyForTrade, currentDate); if (operation != null) { operation.isRebalanced = true; } logger.Debug("Current cash: " + GetCurrentMoneyFormatted()); } else { logger.Info($"No needed to Buy {symbol.Code}"); } } logger.Info($"{currentDate} END REBALANCING. CASH: " + GetCurrentMoneyFormatted()); }
public void Rebalance(Symbol symbol, Rebalancing rebalancing, DateTime currentDate) { Rebalance(new List <Symbol> { symbol }, rebalancing, currentDate); }