Combining Separate Strategy Backtests into a Portfolio View
Summary
This example runs two existing futures strategies independently, using separate instruments, date ranges, trading costs, contract sizes, and capital settings. It then adds their result data frames, removes missing rows, and passes the combined data to a statistics and charting step. The method illustrates a basic workflow for examining multiple strategy results together after individual backtests.
The example uses an ATR and RSI strategy on an index futures contract and a Bollinger channel strategy on a rebar futures contract, both with one-minute data over the same stated period. It provides code but no reported performance figures or interpretation of the chart. The approach therefore does not establish that the combined series is a valid portfolio simulation: adding result frames may not model shared capital, concurrent positions, portfolio-level sizing, or cross-instrument exposure correctly. Those assumptions and the meaning of the resulting statistics need independent verification before drawing conclusions.
Key ideas
- The example backtests two futures strategies separately with instrument-specific trading assumptions.
- It combines the returned data frames before calculating statistics and plotting results.
- A combined chart does not by itself prove that portfolio capital and exposure were modeled jointly.
- The document supplies no performance results or discussion of the plotted output.
Tags
Full text
# portfolio backtesting
```python
from datetime import datetime
from vnpy_ctastrategy.backtesting import BacktestingEngine
from vnpy_ctastrategy.strategies.atr_rsi_strategy import AtrRsiStrategy
from vnpy_ctastrategy.strategies.boll_channel_strategy import BollChannelStrategy
```
```python
def run_backtesting(strategy_class, setting, vt_symbol, interval, start, end, rate, slippage, size, pricetick, capital):
engine = BacktestingEngine()
engine.set_parameters(
vt_symbol=vt_symbol,
interval=interval,
start=start,
end=end,
rate=rate,
slippage=slippage,
size=size,
pricetick=pricetick,
capital=capital
)
engine.add_strategy(strategy_class, setting)
engine.load_data()
engine.run_backtesting()
df = engine.calculate_result()
return df
def show_portafolio(df):
engine = BacktestingEngine()
engine.calculate_statistics(df)
engine.show_chart(df)
```
```python
df1 = run_backtesting(
strategy_class=AtrRsiStrategy,
setting={},
vt_symbol="IF88.CFFEX",
interval="1m",
start=datetime(2019, 1, 1),
end=datetime(2019, 4, 30),
rate=0.3/10000,
slippage=0.2,
size=300,
pricetick=0.2,
capital=1_000_000,
)
```
```python
df2 = run_backtesting(
strategy_class=BollChannelStrategy,
setting={'fixed_size': 16},
vt_symbol="RB88.SHFE",
interval="1m",
start=datetime(2019, 1, 1),
end=datetime(2019, 4, 30),
rate=1/10000,
slippage=1,
size=10,
pricetick=1,
capital=1_000_000,
)
```
```python
dfp = df1 + df2
dfp =dfp.dropna()
show_portafolio(dfp)
```
```python
```
Shown in full with attribution under the source's licence. Licence: MIT
This summary was written by Stratmill's research agent from the original; it is not a copy of the source.