diff --git a/vbt-helper.ipynb b/vbt-helper.ipynb index a91715d..2cdf642 100644 --- a/vbt-helper.ipynb +++ b/vbt-helper.ipynb @@ -2,34 +2,35 @@ "cells": [ { "cell_type": "code", - "execution_count": 4, + "execution_count": 5, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "MACD.run(\n", + "BBANDS.run(\n", " close,\n", - " fastperiod=Default(value=12),\n", - " slowperiod=Default(value=26),\n", - " signalperiod=Default(value=9),\n", + " timeperiod=Default(value=5),\n", + " nbdevup=Default(value=2.0),\n", + " nbdevdn=Default(value=2.0),\n", + " matype=Default(value=0),\n", " timeframe=Default(value=None),\n", - " short_name='macd',\n", + " short_name='bbands',\n", " hide_params=None,\n", " hide_default=True,\n", " **kwargs\n", "):\n", - " Run `MACD` indicator.\n", + " Run `BBANDS` indicator.\n", " \n", " * Inputs: `close`\n", - " * Parameters: `fastperiod`, `slowperiod`, `signalperiod`, `timeframe`\n", - " * Outputs: `macd`, `macdsignal`, `macdhist`\n", + " * Parameters: `timeperiod`, `nbdevup`, `nbdevdn`, `matype`, `timeframe`\n", + " * Outputs: `upperband`, `middleband`, `lowerband`\n", " \n", " Pass a list of parameter names as `hide_params` to hide their column levels, or True to hide all.\n", " Set `hide_default` to False to show the column levels of the parameters with a default value.\n", " \n", - " Other keyword arguments are passed to `MACD.run_pipeline`.\n" + " Other keyword arguments are passed to `BBANDS.run_pipeline`.\n" ] } ], @@ -37,7 +38,7 @@ "import vectorbtpro as vbt\n", "\n", "vbt.IF.list_indicators(\"*SMA\")\n", - "vbt.phelp(vbt.indicator(\"talib:MACD\").run)\n" + "vbt.phelp(vbt.indicator(\"talib:BBANDS\").run)\n" ] } ], diff --git a/vbt.py b/vbt.py index 1d90864..a709f17 100644 --- a/vbt.py +++ b/vbt.py @@ -62,11 +62,18 @@ t1close_realigned = t1data.data["BAC"].close.vbt.realign_closing(resampler_s) #endregion #region ENTRIES/EXITS +#doc from_signal http://5.161.179.223:8000/vbt-doc/api/portfolio/base/#vectorbtpro.portfolio.base.Portfolio.from_signals +- StopExitPrice (Which price to use when exiting a position upon a stop signal?) +- StopEntryPrice (Which price to use as an initial stop price?) + +price = close.vbt.wrapper.fill() +price[entries] = entry_price +price[exits] = exit_price + # window open/close - #END OF DAY EXITS # end_of_day_dates = index.to_series().resample("1d").last().values # exit_signals.loc[end_of_day_dates] = True @@ -75,6 +82,64 @@ df['exit'][df['exit'].index.isin(end_of_day_dates)] = True # This index should be probably open_hours_index # But also check that end_of_day_dates doesn't have nans (NaT), and if it has, you need to filter them out (edited) +#endregion + +#region STOPLOSS/TAKEPROFIT + +#doc StopOrders http://5.161.179.223:8000/vbt-doc/documentation/portfolio/from-signals/index.html#stop-orders + +#SL - ATR based +atr = data.run("atr").atr +pf = vbt.Portfolio.from_signals( + data, + entries=entries, + sl_stop=atr / sub_data.close +) + +#EXIT after time http://5.161.179.223:8000/vbt-doc/cookbook/portfolio/index.html#from-signals +f = vbt.PF.from_signals(..., td_stop="7 days") +pf = vbt.PF.from_signals(..., td_stop=pd.Timedelta(days=7)) +pf = vbt.PF.from_signals(..., td_stop=td_arr) +#EXIT at time +pf = vbt.PF.from_signals(..., dt_stop="16:00") #exit at 16 and later +pf = vbt.PF.from_signals(..., dt_stop=datetime.time(16, 0)) +pf = vbt.PF.from_signals( #exit last bar before + ..., + dt_stop="16:00", + arg_config=dict(dt_stop=dict(last_before=True)) +) + +#CALLBACKS - +""" + - a signal function (signal_func_nb) + - can dynamically generate signals (True, True, False,False) + - runs at beginning of bar + - an adjustment function (adjust_func_nb) + - runs only if signal function above was not provided, but entry,exit arrays + - runs before default signal function ls_signal_func_nb http://5.161.179.223:8000/vbt-doc/api/portfolio/nb/from_signals/index.html#vectorbtpro.portfolio.nb.from_signals.ls_signal_func_nb + - can change pending limit orders etc. + - a post-signal function (post_signal_func_nb) + - post-segment function (post_segment_func_nb) + +all of them are accessing SignalContext (c) as named tuple http://5.161.179.223:8000/vbt-doc/api/portfolio/enums/index.html#vectorbtpro.portfolio.enums.SignalContext +SignalContaxt (contains various metrics) + - last_limit_info - 1D with latest limit order per column + - order_counts + - last_return ... + +""" + +#MEMORY http://5.161.179.223:8000/vbt-doc/cookbook/portfolio/index.html#callbacks +#save an information piece at one timestamp and re-use at a later timestamp + + +#MULTIPLE LIMIT ORDERS at TIME http://5.161.179.223:8000/vbt-doc/cookbook/portfolio/index.html#callbacks + +#IGNORE ENTRIES number of DAYS after losing trade - signal function http://5.161.179.223:8000/vbt-doc/cookbook/portfolio/index.html#callbacks + +#adjust_func_nb http://5.161.179.223:8000/vbt-doc/documentation/portfolio/from-signals/#adjustment + + #endregion @@ -88,6 +153,12 @@ t1vwap_h_real = t1vwap_h.vwap.vbt.realign_closing(resampler_s) t1vwap_d_real = t1vwap_d.vwap.vbt.realign_closing(resampler_s) t1vwap_t_real = t1vwap_t.vwap.vbt.realign_closing(resampler_s) +#BBANDS = vbt.indicator("pandas_ta:BBANDS") +mom_anch_d = AnchoredIndicator("talib:MOM", anchor='30min').run(t1data.data["BAC"].close, timeperiod=10) +mom = vbt.indicator("talib:MOM").run(t1data.data["BAC"].close, timeperiod=10, skipna=True) +#macd = vbt.indicator("talib:MACD").run(t1data.data["BAC"].close) #, timeframe=["1T"]) #, +t1data.ohlcv.data["BAC"].lw.plot(auto_scale=[mom_anch_d, mom]) + #SMA - note for TALIB use skipna=True mom_multi_beztf = vbt.indicator("talib:MOM").run(t1data.close, timeperiod=5, skipna=True) @@ -133,13 +204,19 @@ mom = vbt.indicator("talib:MOM").run(t1data.close, timeperiod=10, skipna=True) t1data.ohlcv.data["BAC"].lw.plot(left=[(mom_daily, "daily_splitter"),(mom, "original mom")]) #OHLCV with indicators on top #TAKING and APPLY AUTOMATIC +daily_splitter = vbt.Splitter.from_grouper(t1data.index, "D", split=None) #DOES contain last DAY def indi_run(sr): return vbt.indicator("talib:MOM").run(sr.close, timeperiod=10, skipna=True) -res = daily_splitter.apply(indi_run, vbt.Takeable(sr), merge_func="row_stack", freq="1T") +res = daily_splitter.apply(indi_run, vbt.Takeable(t1data), merge_func="row_stack", freq="1T") +#use of IDX accessor (docs:http://5.161.179.223:8000/vbt-doc/api/base/accessors/index.html#vectorbtpro.base.accessors.BaseIDXAccessor) +daily_grouper = t1data.index.vbt.get_grouper("D") +#grouper instance can be iterated over +for name, indices in daily_grouper.iter_groups(): + print(name, indices) #PANDAS GROUPING - series/df grouping resulting in GroupBySeries placeholder that can be aggregated(sum, mean), transformed iterated over or fitlered for name, group in t1data.data["BAC"].close.groupby(pd.Grouper(freq='D')): @@ -176,4 +253,25 @@ ch = chart([pane1], size="s") +#endregion + +#region MULTIACCOUNT +#simultaneous LONG and short (hedging) +#VBT: One position requires one column of data, so hedging is possible by using two columns representing the same asset but different directions, +# then stack both portfolio together (http://5.161.179.223:8000/vbt-doc/features/productivity/#column-stacking) +pf_join = vbt.PF.column_stack((pf1, pf2), group_by=True) + + +#endregion + +#region CUSTOM SIMULATION + + + +#endregion + + +#region ANALYSIS + + #endregion \ No newline at end of file