Sometimes, you have a great idea for an algorithmic trading strategy, but, after employing it, you find that maybe the drawdown is very bad. Then, what you want to be able to do is know exactly what kinds of things you can do to fix this. It also makes a lot of sense to know about some of the major risk metrics out of the gate, so, as you develop your strategy, you create your strategy around known risk metrics. In the case of Quantopian, we know that their main metric that they want to see, if you want to enter into their competition, is a low Beta. Beta is a measurement of how your strategy moves with the market movements. A Beta of positive 1 means your strategy is going to move with the market. By the very nature of a "trading" strategy, you are introducing more risk usually than if you just bought and held. If your Beta is 1, then it makes no sense to be trading in the markets, because you'd be a lot safer just buying and holding.
A lower than 1 beta is good, but, as you approach -1 (negative 1), we're back into dangerous-ville. Quantopian, for example, requires strategies for their contest to have a beta in the range of -0.3 to 0.3. We will talk more about this later on, but I assume many people reading and following along in this tutorial may actually be interested in being employed somewhere as an algorithmic trader. Probably the most important thing you will need to have in order to get employed is a firm understanding of risk metrics like this, and how to devise a strategy to suit your employer's interests. It is often the case, with things like hedgefunds or corporations, that the goal is not necessarily to create a return from the trading. It is instead to hedge the market they otherwise have a large amount of exposure in.
Is a Beta close to zero always the best or most desireable? No. Investing and trading can take on many forms: Steady income, asset protection, market hedging, and more. Depending on the objectives, you or your employer might be interested in different types of strategies. We will discuss later in this series the objectives of hedgefunds and why people may want various forms of algorithms and strategies.
Since this -0.30 - 0.3 Beta is the main metric being sought after, how might we achieve this? We mainly need to be "hedged" as evenly as possible, meaning that we are ideally doing both investing and shorting.
To build our strategy, we're going to invest purely into market sectors. The Spyder Index funds have 9 major sectors in the form of ETFs (exchange traded funds), so we can use those.
First step here is to set up our universe in our
def initialize(context): context.stocks = symbols('XLY', # XLY Consumer Discrectionary SPDR Fund 'XLF', # XLF Financial SPDR Fund 'XLK', # XLK Technology SPDR Fund 'XLE', # XLE Energy SPDR Fund 'XLV', # XLV Health Care SPRD Fund 'XLI', # XLI Industrial SPDR Fund 'XLP', # XLP Consumer Staples SPDR Fund 'XLB', # XLB Materials SPDR Fund 'XLU') # XLU Utilities SPRD Fund
Next, we need some sort of strategy. The idea here is that sectors will move at least somewhat differently. The easiest thing we can do is set up a simple moving average crossover strategy, per ETF. Then, if the shorter moving average is above the larger moving average, we want to be invested in the ETF. If the shorter moving average is below the longer one, then we want to short the company. This means we will always have a position in regards to each ETF, as well as meaning we will at least be likely longing (invested in, bought shares) and shorting (betting against by selling lent shares from someone else with the intention to buy back cheaper later) various ETFs. To do this, we'll set up our
def handle_data(context, data): for stock in context.stocks: ma1 = data[stock].mavg(50) ma2 = data[stock].mavg(200) price = data[stock].price if ma1 > ma2: order_target_percent(stock, 0.11) elif ma1 < ma2: order_target_percent(stock, -0.11)
Notice here that we're using the
order_target_percent method for ordering shares.
Because we have 9 plausible companies, we're willing to target up to 11% of our portfolio towards the companies. Even though having -11% means we have the money left over (remember, shorting means you are borrowing shares). Just because you can short companies and still have 100% of your funds left over to invest, it doesn't mean you should, since this will accrue leverage.
One nice thing about this strategy is it is incredibly simple. You don't need to bother with various checks and balances, since you are either long or short, you don't need to worry about if you have the funds, and so on, because we're buying in percentage form, and we're only investing with money we have. Also, logically, it's very simple, there's no reason to check to see if we already have positions in the company, since we're using target_percent. If we're already at the target percent, then great! Finally, it keeps us diversified, since we're in the assortment of sectors, and we're enforcing portfolio balance with the target_percentages. If suddenly value in one ETF goes up 20%, and down 30% in another, this strategy will automatically balance this out.
In my book, simple is best, and this is probably one of the best starting points for a strategy in this entire series.
Full code up to now is just:
def initialize(context): context.stocks = symbols('XLY', # XLY Consumer Discrectionary SPDR Fund 'XLF', # XLF Financial SPDR Fund 'XLK', # XLK Technology SPDR Fund 'XLE', # XLE Energy SPDR Fund 'XLV', # XLV Health Care SPRD Fund 'XLI', # XLI Industrial SPDR Fund 'XLP', # XLP Consumer Staples SPDR Fund 'XLB', # XLB Materials SPDR Fund 'XLU') # XLU Utilities SPRD Fund def handle_data(context, data): for stock in context.stocks: ma1 = data[stock].mavg(50) ma2 = data[stock].mavg(200) price = data[stock].price if ma1 > ma2: order_target_percent(stock, 0.11) elif ma1 < ma2: order_target_percent(stock, -0.11)
Now we're cooking! With this extremely simple strategy, we're already showing great returns, and we're within the Beta range that we want!
We'd like to see alpha up a bit, and we'd also like to get a better handle on that 33% drawdown. Max drawdown is a measure of the largest difference of any peak in performance and subsequent drop. We'd also like to see a higher Sharpe Ratio. Definitely above 1. Above 2 is good. Above 3 is superb. The sharpe ratio is a measure of the returns compared to the risk you took to achieve them, so this is often referred to as the "gold standard" in trading algorithms.
Keep this strategy in mind, but we're actually going to be moving away from it for now, as we approach a new topic,
fetch_csv. This new method will allow us to grab a CSV file from the internet and incoporate it into our trading strategy.