5 Powerful Use Cases of the vectorBT Library for Algorithmic Trading
Kevin Meneses
SAP CX Senior Consultant |SAP Sales and Service Cloud|CPI|CDC|Qualtrics|Data Analyst and ETL|Marketing Automation|SAPMarketing Cloud and Emarsys
If you’re a trader or data scientist interested in building robust trading strategies, you’ve likely encountered the challenge of backtesting and optimizing strategies efficiently. This is where vectorBT shines. Built on top of powerful libraries like NumPy and Pandas, vectorBT enables traders to test, optimize, and analyze trading strategies with ease, all while handling vast datasets. In this article, we’ll explore five practical use cases that demonstrate how vectorBT can elevate your trading analysis, from simple technical indicators to portfolio simulations and optimization.
1. Simple Backtesting Using Technical Indicators
One of the most basic yet powerful uses of vectorBT is testing trading strategies based on technical indicators. Let’s consider a simple moving average crossover strategy, where the strategy buys when the price crosses above the 50-day moving average and sells when it crosses below.
Code Example:
import vectorbt as vbt
import pandas as pd
import numpy as np
# Download historical data
data = vbt.YFData.download('AAPL', start='2020-01-01', end='2021-12-31').get('Close')
# Create moving averages using pandas
fast_ma = data.rolling(window=50).mean() # 50-day moving average
slow_ma = data.rolling(window=200).mean() # 200-day moving average
# Define entry and exit rules
entries = fast_ma > slow_ma # Entry signal: 50-day MA crosses above 200-day MA
exits = fast_ma < slow_ma # Exit signal: 50-day MA crosses below 200-day MA
# Run backtesting
portfolio = vbt.Portfolio.from_signals(data, entries, exits)
# Print total return
print(portfolio.total_return())
# Optional: plot the portfolio performance
portfolio.plot().show()
Results
the total return obtained was 0.47%
Explanation: In this example, we download historical price data for Apple (AAPL) and compute two moving averages: the 50-day and the 200-day. The strategy buys when the 50-day moving average crosses above the 200-day (bullish signal) and sells when it crosses below (bearish signal). The portfolio’s total return is calculated at the end.
2. Strategy Parameter Optimization
One of vectorBT’s standout features is the ability to easily optimize strategy parameters. For instance, let’s optimize the moving average lengths in the crossover strategy to find the best-performing parameters.
import vectorbt as vbt
import pandas as pd
import numpy as np
# Download historical data
data = vbt.YFData.download('AAPL', start='2020-01-01', end='2021-12-31').get('Close')
# Define ranges for fast and slow moving averages
fast_ma_range = range(10, 100, 10) # Short moving averages from 10 to 90 in steps of 10
slow_ma_range = range(100, 300, 20) # Long moving averages from 100 to 280 in steps of 20
# Store the results
results = {}
# Loop over all combinations of fast and slow MA values
for fast_ma in fast_ma_range:
for slow_ma in slow_ma_range:
if fast_ma >= slow_ma:
continue # Fast MA should always be less than slow MA to make sense
# Calculate moving averages
fast_ma_values = data.rolling(window=fast_ma).mean()
slow_ma_values = data.rolling(window=slow_ma).mean()
# Define entry and exit signals
entries = fast_ma_values > slow_ma_values
exits = fast_ma_values < slow_ma_values
# Run backtesting
portfolio = vbt.Portfolio.from_signals(data, entries, exits)
# Store total return for each combination of fast_ma and slow_ma
results[(fast_ma, slow_ma)] = portfolio.total_return()
# Convert results to a DataFrame for better visualization
results_df = pd.DataFrame.from_dict(results, orient='index', columns=['Total Return'])
# Find the best combination
best_params = results_df['Total Return'].idxmax()
best_return = results_df['Total Return'].max()
print(f"Best MA combination: Fast MA = {best_params[0]}, Slow MA = {best_params[1]}")
print(f"Best Total Return: {best_return}")
here I obtained the following:
Best MA combination: Fast MA = 50, Slow MA = 100 Best
Total Return: 1.1302656073899642
Explanation: Here, we test various combinations of short and long moving averages, running backtests for each. vectorBT runs all backtests in parallel, making it extremely efficient. Finally, we find the best parameters based on total return.
3. Simulating a Diversified Portfolio
Another common use case is backtesting a diversified portfolio of multiple assets. With vectorBT, you can simulate strategies across a portfolio and evaluate how a strategy performs on different assets simultaneously.
Code Example:
import vectorbt as vbt
import pandas as pd
import numpy as np
# Download data for multiple assets
tickers = ['AAPL', 'GOOG', 'MSFT', 'TSLA']
data = vbt.YFData.download(tickers, start='2020-01-01', end='2021-12-31').get('Close')
# Create moving averages for each asset
fast_ma = data.rolling(window=50).mean() # 50-day moving average
slow_ma = data.rolling(window=200).mean() # 200-day moving average
# Define entry and exit rules based on moving averages
entries = fast_ma > slow_ma # Entry signal: fast MA crosses above slow MA
exits = fast_ma < slow_ma # Exit signal: fast MA crosses below slow MA
# Run portfolio backtesting
portfolio = vbt.Portfolio.from_signals(data, entries, exits, init_cash=100_000, freq='1D')
# Show total returns per asset
print(f"Total Return:\n{portfolio.total_return()}")
# Check trades log for any issues
print("Trade Logs:\n", portfolio.trades.records_readable)
领英推荐
Code output
Total Return: symbol AAPL 0.487929 GOOG 0.872871 MSFT 0.561778 TSLA 1.143186
Explanation: In this example, we create a portfolio consisting of four stocks (Apple, Google, Microsoft, Tesla) and apply the same moving average crossover strategy to each. The portfolio’s overall performance is calculated and printed out
4. Custom Signal-Based Strategies
vectorBT allows users to define custom trading signals based on any condition. Whether it’s technical indicators, price patterns, or market events, you can easily build and backtest a strategy around these signals.
Code Example:
import vectorbt as vbt
import pandas as pd
import numpy as np
# Download historical data for multiple assets
tickers = ['AAPL', 'GOOG', 'MSFT', 'TSLA']
data = vbt.YFData.download(tickers, start='2020-01-01', end='2021-12-31').get('Close')
# Define custom entry signal: Buy when the price increases by more than 3% in a single day
entries = data.pct_change() > 0.03
# Define custom exit signal: Sell when the price decreases by more than 2% in a single day
exits = data.pct_change() < -0.02
# Run portfolio backtesting
portfolio = vbt.Portfolio.from_signals(data, entries, exits, init_cash=100_000, freq='1D')
# Show total return per asset
print(f"Total Return per asset:\n{portfolio.total_return()}")
# Check trades log for any issues
print("Trade Logs:\n", portfolio.trades.records_readable)
Code output
Total Return per asset: symbol AAPL -0.035499 GOOG -0.228541 MSFT -0.399596 TSLA 7.180662
Explanation: In this case, the strategy buys when the price jumps more than 3% in one day and sells when it falls by more than 2%. This type of custom rule creation is highly flexible and can be adapted for many use cases.
5. Volatility-based strategy using ATR (Average True Range)
The Average True Range (ATR) is a volatility indicator that measures the degree of price volatility in an asset. A volatility-based strategy can use the ATR to define entry and exit points, or even to dynamically adjust position sizing based on market volatility.
Code Example: ATR-Based Volatility Strategy
import vectorbt as vbt
import pandas as pd
import pandas_ta as ta
# Download historical data
tickers = ['AAPL']
data = vbt.YFData.download(tickers, start='2020-01-01', end='2021-12-31').get(['High', 'Low', 'Close'])
# Calculate ATR using pandas_ta
data['ATR'] = ta.atr(data['High'], data['Low'], data['Close'], length=14)
# Define a threshold based on ATR (average ATR * 1.5)
threshold = data['ATR'].mean() * 1.5
# Define entry and exit signals based on ATR
entries = data['ATR'] > threshold # Enter when ATR is above the threshold (high volatility)
exits = data['ATR'] < threshold # Exit when ATR is below the threshold (low volatility)
# Backtest the strategy
portfolio = vbt.Portfolio.from_signals(data['Close'], entries, exits, init_cash=100_000)
# Show total return per asset
print(f"Total Return: {portfolio.total_return()}")
# Plot the portfolio's performance
portfolio.plot().show()
Explanation:
Conclusion
These five examples demonstrate the versatility of vectorBT for developing and backtesting various trading strategies, including mean reversion, momentum trading, pairs trading, dynamic asset allocation, and volatility-based strategies. With its ability to handle a wide range of technical indicators and perform efficient backtesting, vectorBT is a powerful tool for quantitative finance and algorithmic trading.
Follow me on Linkedin https://www.dhirubhai.net/in/kevin-meneses-897a28127/
Subscribe to the Data Pulse Newsletter :https://www.dhirubhai.net/newsletters/datapulse-python-finance-7208914833608478720Join