| Overall Statistics |
|
Total Trades 302 Average Win 1.12% Average Loss -0.04% Compounding Annual Return 33.038% Drawdown 0.300% Expectancy 26.974 Net Profit 358.464% Sharpe Ratio 0.459 Probabilistic Sharpe Ratio 0.017% Loss Rate 7% Win Rate 93% Profit-Loss Ratio 28.96 Alpha 0.545 Beta 0.049 Annual Standard Deviation 1.186 Annual Variance 1.407 Information Ratio 0.457 Tracking Error 1.188 Treynor Ratio 11.082 Total Fees â‚¿0.08 Estimated Strategy Capacity â‚¿0 Lowest Capacity Asset LTCBTC E3 |
#region imports
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Globalization;
using System.Drawing;
using QuantConnect;
using QuantConnect.Algorithm.Framework;
using QuantConnect.Algorithm.Framework.Selection;
using QuantConnect.Algorithm.Framework.Alphas;
using QuantConnect.Algorithm.Framework.Portfolio;
using QuantConnect.Algorithm.Framework.Execution;
using QuantConnect.Algorithm.Framework.Risk;
using QuantConnect.Parameters;
using QuantConnect.Benchmarks;
using QuantConnect.Brokerages;
using QuantConnect.Util;
using QuantConnect.Interfaces;
using QuantConnect.Algorithm;
using QuantConnect.Indicators;
using QuantConnect.Data;
using QuantConnect.Data.Consolidators;
using QuantConnect.Data.Custom;
using QuantConnect.DataSource;
using QuantConnect.Data.Fundamental;
using QuantConnect.Data.Market;
using QuantConnect.Data.UniverseSelection;
using QuantConnect.Notifications;
using QuantConnect.Orders;
using QuantConnect.Orders.Fees;
using QuantConnect.Orders.Fills;
using QuantConnect.Orders.Slippage;
using QuantConnect.Scheduling;
using QuantConnect.Securities;
using QuantConnect.Securities.Equity;
using QuantConnect.Securities.Future;
using QuantConnect.Securities.Option;
using QuantConnect.Securities.Forex;
using QuantConnect.Securities.Crypto;
using QuantConnect.Securities.Interfaces;
using QuantConnect.Storage;
using QuantConnect.Data.Custom.AlphaStreams;
using QCAlgorithmFramework = QuantConnect.Algorithm.QCAlgorithm;
using QCAlgorithmFrameworkBridge = QuantConnect.Algorithm.QCAlgorithm;
#endregion
namespace QuantConnect.Algorithm.CSharp
{
public class VentralTransdimensionalChamber : QCAlgorithm
{
// Trading bot that trades with the highest and lowest exchange rate of the last 24 hours.
// Buying determined bacause the factor, MACD and the current price.
private Dictionary<Symbol, SymbolData> _dataBySymbol;
// VARIABELEN DECLAREREN
//private decimal _targetPercent = .008m;
private decimal _targetPercent = .01m; //Sell when 1% profit
private decimal _stopPercent = .10m; //Sell when loss is 10%
//TrailPercentage
//private decimal _trailPercent = .07m;
decimal _minPosition = .05m; // min BTC needed to invest.
public decimal _btc;
public string valuta = "BTC";
public decimal _holding;
//ORDERSIZE
private decimal usdAmount = 500.0m; //size in USD we want to invest.
private Symbol btcusd;
private decimal _btcStijging = 0.5m;
Resolution res = Resolution.Minute;
//MACD VARIABLES
public int RollingWindow = 5;
RollingWindow<IndicatorDataPoint> _macdWin;
MovingAverageConvergenceDivergence _macd;
MomentumPercent _momentumPercent;
private decimal pipProfit;
decimal macd_change;
public decimal _VolumeMinimum = 1000000;
//RSI Variabelen
RelativeStrengthIndex _rsi;
//INITIALIZE BLOCK
public override void Initialize()
{
SetStartDate(2017, 1, 1);
SetEndDate(2022, 5, 1);
SetAccountCurrency(valuta);
SetCash("BTC", 1);
SetBrokerageModel(BrokerageName.Bitfinex, AccountType.Cash);
btcusd = AddCrypto("BTCUSD", Resolution.Minute).Symbol;
int MomentumPercentPeriod = 1440; //1dag = 1440, 2dagen = 2880, 3dagen = 4320, 4dagen = 5760, 5dagen = 7200, 6dagen = 8640, 7dagen = 10080, 8dagen = 11520, 9dagen = 12960, 10dagen = 14400
_momentumPercent = MOMP("BTCUSD", MomentumPercentPeriod, Resolution.Minute);
SetWarmUp(MomentumPercentPeriod, Resolution.Minute);
_dataBySymbol = new Dictionary<Symbol, SymbolData>();
foreach (var ticker in new [] {"ETHBTC", "LTCBTC","EOSBTC", "ADABTC"})
//, "DOTBTC", "LINKBTC", "SOLBTC", "MATICBTC", "XMRBTC", "UNIBTC", "VETBTC", "TRXBTC", "EGLDBTC", "AVAXBTC", "XTZBTC", "WAVESBTC", "FTMBTC"
/*"ETHBTC", "ADABTC", "DOTBTC", "AXSBTC", "LINKBTC", "RUNEBTC", "SOLBTC", "MATICBTC", "XMRBTC", "UNIBTC", "ALICEBTC", "VETBTC", "TLMBTC",
"COMPBTC", "SUSHIBTC", "FILBTC", "SANDBTC", "CAKEBTC", "CRVBTC", "NEOBTC", "XLMBTC", "FETBTC", "TRXBTC", "ATOMBTC",
"RVNBTC", "KAVABTC", "SXPBTC", "STORJBTC", "NMRBTC", "1INCHBTC", "ETCBTC", "CHZBTC", "TFUELBTC", "ALGOBTC","AAVEBTC",
"EGLDBTC", "ZILBTC", "AVAXBTC", "OMGBTC", "SNXBTC", "NANOBTC", "MANABTC", "KSMBTC", "ENJBTC", "NEARBTC", "XTZBTC", "IOTABTC", "DASHBTC", "HBARBTC", "FTTBTC",
"WAVESBTC", "AUDIOBTC", "IOSTBTC", "CELRBTC", "HNTBTC", "ALPHABTC", "ZECBTC", "ICXBTC", "LTCBTC",
"COTIBTC", "FTMBTC", "ONEBTC", "CHRBTC", "ARBTC", "CTSIBTC", "GRTBTC",
"ANKRBTC", "GASBTC", "ARPABTC", "KNCBTC", "ADXBTC", "TVKBTC", "OGNBTC", "LRCBTC", "ONTBTC",
"RENBTC", "DIABTC", "SUPERBTC", "BAKEBTC", "THETABTC" */
{
var crypto = AddCrypto(ticker, res);
_dataBySymbol.Add(crypto.Symbol, new SymbolData(this, crypto));
}
SetWarmUp(3 * SymbolData.MinutesOfTrading, res);
//SetWarmUp(SymbolData.MinutesOfTrading, Resolution.Minute);
}
private decimal NormalizeQuantity(Symbol symbol, decimal quantity)
{
var pip = Securities[symbol].SymbolProperties.MinimumPriceVariation;
return Math.Round(quantity/pip) * pip;
}
// ON DATA BLOCK (waar bestanden/data binnenkomt in het programma)
public override void OnData(Slice data)
{
if (IsWarmingUp) return;
if (!_momentumPercent.IsReady) return;
foreach (var kvp in _dataBySymbol)
{
var symbolData = kvp.Value;
if (!symbolData.IsReady)
{
continue;
}
var symbol = kvp.Key;
if (!data.Bars.ContainsKey(symbol))
{
continue;
}
if (!data.ContainsKey(symbol) | !data.ContainsKey("BTCUSD")) // !data.ContainsKey(symbol)
{
return;
}
//Calculate usdAmount to BtcAmount
var btcAmount = usdAmount / data[btcusd].Close;
//DETERMINE WHAT THE VALUE OF $150 USD IS IN BTC
Plot("150 USD in BTC", "Value", btcAmount);
var price = data[symbol].Price;
var invested = Portfolio[symbol].Invested;
_btc = Portfolio.CashBook[valuta].Amount;
//_volume = data.Bars[symbol].Volume;
//Log Message for checking if we getting Data!
if (LiveMode)
{
var msg = $"\n{symbol} :: IsInvested? {invested} | Factor: {symbolData.Factor} | ";
msg += $"LowestAvg: {symbolData.LowestAverage} | Price: {price} | MACD Change: {symbolData.MacdChange} | BTC 24h change %: {_momentumPercent} | Portfolio Amount: {_btc}\n";
Log(msg);
}
//BUYING PART!!
if (!invested && symbolData.Factor >= 3 && symbolData.LowestAverage >= price && _momentumPercent > _btcStijging && _btc > _minPosition) // && _momentumPercent >= _btcStijging && _btc > _minPosition
{
if (symbolData.MacdChange >= 0 && symbolData._rsi <= 20)//&& symbolData.MacdChange < 2
{
//Determine order size.
var quantity = NormalizeQuantity(symbol, btcAmount / data[symbol].Close);
//var msg = $"\n\n AANKOOP ter waarde van {btcAmount} BTC | {symbol} Hoeveelheid: {quantity} voor een bedrag van {usdAmount} euro | Aankoopprijs {symbol} van {data[symbol].Price}BTC\n\n";
//Log(msg);
//Debug(msg);
if (quantity == 0) continue;
//Placing Order
MarketOrder(symbol, quantity);
Plot("Trades", "AANKOOP", price);
Debug($"\n\n ********** AANKOOP: {symbol} aankoopprijs {data[symbol].Price} ter waarde van {usdAmount}euro **********\n\n"); // Als het order gemaakt is word dit bevestigd door de debug
//Sending message to telegram group
Notify.Telegram("-100155824763**", $"Aankoopmogelijkheid {symbol} met aankoopprijs: {data[symbol].Price}", "**087994843:AAGz-tc6Jc5rXuHtNSQcWAJVZygTlZSpUdE");
//Sending message to mail
Notify.Email("tradingbot*******@gmail.com", "TradeAlert",$"Gekocht {symbol} op {data[symbol].Price}");
//Log message
Log($"prijs {price} en Max 24uur {symbolData.MaxExchange} en MIN 24uur {symbolData.MinExchange}");
//Determine Which selling price.
symbolData.TargetPrice = price * (1 + _targetPercent); //DETERMINE WICH SELLING PRICE WHEN PROFIT.
symbolData.StopPrice = price * (1 - _stopPercent); //DETERMINE WICH SELLING PRICE WHEN LOSS.
//symbolData.StopPrice = Math.Max(symbolData.StopPrice, price - (price * _trailPercent));
}
}
//SELLING PART!!
if (invested)
{
//Selling with GAIN
if (price >= symbolData.TargetPrice)
{
Debug($"\n\n********** VERKOOP WINST: {symbol} {data[symbol].Price} **********\n\n "); // Als het order gemaakt is word dit bevestigd door de debug
Plot("BTC", "Holdings", Portfolio.CashBook["BTC"].Amount);
Plot("Trades", "VERKOOP WINST \n", price);
var tag = $"+1% WINST VERKOCHT {symbol} op {data[symbol].Price}";
//Sell Order
Liquidate(symbol, tag);
//log message
Log(tag);
//Sending message to telegram group
Notify.Telegram("-100155824763**", $"VERKOOP WINST {symbol} met verkoopprijs: {data[symbol].Price}", "**087994843:AAGz-tc6Jc5rXuHtNSQcWAJVZygTlZSpUdE");
//Sending message to mail
Notify.Email("tradingbot*******@gmail.com", "TradeAlert", tag);
}
//Selling with Loss
if (price < symbolData.StopPrice)
{
Debug($"\n\n********** VERKOOP VERLIES: {symbol} {data[symbol].Price} van een bedrag van {usdAmount}euro ********** \n\n"); // Als het order gemaakt is word dit bevestigd door de debug
Plot("BTC", "Holdings", Portfolio.CashBook["BTC"].Amount);
Plot("Trades", "VERKOOP VERLIES \n", price);
var tag = $"-10% VERLIES VERKOCHT {symbol} op {data[symbol].Price}";
//Sell order
Liquidate(symbol, tag);
//Log message
Log(tag);
//Sending message to mail
Notify.Telegram("-100155824763***", $"VERKOOP VERLIES {symbol} met verkoopprijs: {data[symbol].Price}", "***087994843:AAGz-tc6Jc5rXuHtNSQcWAJVZygTlZSpUdE");
//Sending message to mail
Notify.Email("tradingbot*****@gmail.com", "TradeAlert", tag);
}
}
}
}
}
public class SymbolData
{
private Cash _cash;
public static int MinutesOfTrading = 1140;
int MomentumPercentPeriod = 1440;
public decimal StopPrice;
public decimal TargetPrice;
//Macd
public int fast = 12; //12 5
public int slow = 26; //26 35
public int sig = 9; //9 5
//RSI
public Minimum _minCustom;
public Maximum _maxCustom;
public decimal Holding => _cash.Amount;
public Maximum MaxExchange { get; private set; }
public Minimum MinExchange { get; private set; }
public MovingAverageConvergenceDivergence _macd {get; private set;}
public RollingWindow<IndicatorDataPoint> _macdWin {get; private set;}
public RelativeStrengthIndex _rsi {get; private set;}
public bool IsReady => MaxExchange.IsReady && MinExchange.IsReady && _macdWin.IsReady && _macd.IsReady; //&& _rsi.IsReady;
public decimal MacdChange =>(_macdWin[0] - _macdWin[_macdWin.Count - 1]);
public decimal Factor => (((MaxExchange - MinExchange)/2)/MaxExchange)*100;
decimal percentage = 2.1m;
public decimal LowestAverage => ((MaxExchange + MinExchange)/2 + MinExchange)/percentage;
public SymbolData(QCAlgorithm algorithm, Crypto crypto)
{
Resolution resM = Resolution.Minute;
//Resolution resH = Resolution.Hour;
_cash = algorithm.Portfolio.CashBook[crypto.BaseCurrencySymbol];
MaxExchange = algorithm.MAX(crypto.Symbol, MinutesOfTrading, resM);
MinExchange = algorithm.MIN(crypto.Symbol, MinutesOfTrading, resM);
_macd = algorithm.MACD(crypto.Symbol, fast, slow, sig, MovingAverageType.Exponential,resM);
_macdWin = new RollingWindow<IndicatorDataPoint>(5);
_macd.Signal.Updated +=(sender, updated) => _macdWin.Add(updated);
_rsi = algorithm.RSI(crypto.Symbol, 4, MovingAverageType.Simple, resM);
}
}
}
#region imports
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Globalization;
using System.Drawing;
using QuantConnect;
using QuantConnect.Algorithm.Framework;
using QuantConnect.Algorithm.Framework.Selection;
using QuantConnect.Algorithm.Framework.Alphas;
using QuantConnect.Algorithm.Framework.Portfolio;
using QuantConnect.Algorithm.Framework.Execution;
using QuantConnect.Algorithm.Framework.Risk;
using QuantConnect.Parameters;
using QuantConnect.Benchmarks;
using QuantConnect.Brokerages;
using QuantConnect.Util;
using QuantConnect.Interfaces;
using QuantConnect.Algorithm;
using QuantConnect.Indicators;
using QuantConnect.Data;
using QuantConnect.Data.Consolidators;
using QuantConnect.Data.Custom;
using QuantConnect.DataSource;
using QuantConnect.Data.Fundamental;
using QuantConnect.Data.Market;
using QuantConnect.Data.UniverseSelection;
using QuantConnect.Notifications;
using QuantConnect.Orders;
using QuantConnect.Orders.Fees;
using QuantConnect.Orders.Fills;
using QuantConnect.Orders.Slippage;
using QuantConnect.Scheduling;
using QuantConnect.Securities;
using QuantConnect.Securities.Equity;
using QuantConnect.Securities.Future;
using QuantConnect.Securities.Option;
using QuantConnect.Securities.Forex;
using QuantConnect.Securities.Interfaces;
using QuantConnect.Storage;
using QuantConnect.Data.Custom.AlphaStreams;
using QCAlgorithmFramework = QuantConnect.Algorithm.QCAlgorithm;
using QCAlgorithmFrameworkBridge = QuantConnect.Algorithm.QCAlgorithm;
#endregion
namespace QuantConnect.Algorithm.CSharp
{
}
/*
using QuantConnect.Securities.Crypto;
namespace QuantConnect.Algorithm.CSharp
{
public class VentralTransdimensionalChamber : QCAlgorithm
{
// Trading bot that trades with the highest and lowest exchange rate of the last 24 hours.
// Buying determined bacause the factor and the current price.
private Dictionary<Symbol, SymbolData> _dataBySymbol;
// VARIABELEN DECLAREREN
private string _ticker = "ETHEUR"; //virtueel paar - tracks the current USD value of 1 ether.
private int _startingCash = 2000;
private decimal _weight = 1m; ///Percentage van portfolio dat je wilt investeren // % of portfolio for every trade.
private decimal _targetPercent = .01m; //1% winst dan verkopen // Sell when 1% profit
private decimal _stopPercent = .10m; //verkopen bij de 10% verlies / Sell when loss is 10%
int _maxPosition = 900; // Max USD invested
int _minPosition = 750; // min USD needed to invest.
//INITIALIZE BLOCK
public override void Initialize()
{
SetStartDate(2017, 1, 3);
SetEndDate(2018, 1, 1);
SetCash("EUR", _startingCash);
SetBrokerageModel(BrokerageName.GDAX, AccountType.Cash);
_dataBySymbol = new Dictionary<Symbol, SymbolData>();
foreach (var ticker in new [] { "ETHEUR" })
{
var crypto = AddCrypto(ticker, Resolution.Minute);
_dataBySymbol.Add(crypto.Symbol, new SymbolData(this, crypto));
}
SetWarmUp(SymbolData.MinutesOfTrading, Resolution.Minute);
}
// ON DATA BLOCK (waar bestanden/data binnenkomt in het programma)
public override void OnData(Slice data)
{
if (IsWarmingUp) return;
foreach (var kvp in _dataBySymbol)
{
var symbolData = kvp.Value;
if (!symbolData.IsReady)
{
continue;
}
var symbol = kvp.Key;
if (!data.Bars.ContainsKey(symbol))
{
continue;
}
var price = data[symbol].Price;
var invested = Portfolio[symbol].Invested;
if (!invested &&
symbolData.Factor >= 3)// &&
//symbolData.LowestAverage > price)
{
var qnty = CalculateOrderQuantity(symbol, _weight);
SetHoldings(symbol, _weight); // om een order te maken ==>percentage van portfolio dat je wilt investeren
Debug($"Purchased Stock: {symbol}"); // Als het order gemaakt is word dit bevestigd door de debug
//Log($"prijs {price} en Max 24uur {symbolData.MaxExchange} en MIN 24uur symbolData.MinExchange}");
symbolData.TargetPrice = price * (1 + _targetPercent); //Bepalen welke verkoopprijs bij winst (huidige prijs + 1%) // determine wich selling price at profit
symbolData.StopPrice = price * (1 - _stopPercent); //bepalen welke verkoopprijs bij verlies (huidige - 2%) // determine wich selling price at loss.
}
if (invested)
{
if (price >= symbolData.TargetPrice)
{
Sell(symbol, symbolData.Holding);
//Log($"prijs {price}");
}
if (price < symbolData.StopPrice)
{
Sell(symbol, symbolData.Holding);
//Log($"prijs {price}");
}
}
}
}
}
public class SymbolData
{
private Cash _cash;
public static int MinutesOfTrading = 1140;
public decimal StopPrice;
public decimal TargetPrice;
//Het aantal Ether we in onze portfolio hebben zitten.
public decimal Holding => _cash.Amount;
public Maximum MaxExchange { get; private set; }
public Minimum MinExchange { get; private set; }
public bool IsReady => MaxExchange.IsReady && MinExchange.IsReady;
public decimal Factor => (((MaxExchange - MinExchange)/2)/MaxExchange)*100;
public decimal LowestAverage => ((MaxExchange + MinExchange)/2 + MinExchange)/2;
public SymbolData(QCAlgorithm algorithm, Crypto crypto)
{
_cash = algorithm.Portfolio.CashBook[crypto.BaseCurrencySymbol];
MaxExchange = algorithm.MAX(crypto.Symbol, MinutesOfTrading, Resolution.Minute);
MinExchange = algorithm.MIN(crypto.Symbol, MinutesOfTrading, Resolution.Minute);
}
}
}
*/