Here is a code snippet for calculating a position size in the Forex markets. Position sizing took me a bit longer to wrap my head around than I was expecting so I thought it would make a good post.

### Scope

The aim of this function is to provide the correct position size based on how much of the account you are willing to risk and how far you intend to place your stop loss from the current price.

Another note is that this is designed to for trading on Oanda where there are no minimum lot sizes. On Oanda I can place orders 10, 105 or 2,810,245 units instead of being bound by fixed steps of 1,000 (Micro lots), 10,000 (Mini lots) or 100,000 (full lots) and so on. This is great for those with small account sizes.

If you want to use this code and ARE bound by minimum lot sizes, you will need to add some code to round the units down to the nearest minimum lot. Perhaps something I will code later…..

### Requirements

This script uses the Backtrader backtesting framework, As such it is required due to a call to :

1 |
self.broker.getvalue() |

However this script could be tweaked to include an input parameter for account value so that the code can be used in other frameworks. If you are new to backtrader or Python in general this may not be the article for you. First have a look at the Backtrader: First Script or Getting Setup: Python and Backtrader for more begging focused content.

### The Code

Without further ado, here is the code, some commentary to follow:

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
def size_position(self, price, stop, risk, method=0, exchange_rate=None, JPY_pair=False): ''' Helper function to calcuate the position size given a known amount of risk. *Args* - price: Float, the current price of the instrument - stop: Float, price level of the stop loss - risk: Float, the amount of the account equity to risk *Kwargs* - JPY_pair: Bool, whether the instrument being traded is part of a JPY pair. The muliplier used for calculations will be changed as a result. - Method: Int, - 0: Acc currency and counter currency are the same - 1: Acc currency is same as base currency - 2: Acc currency is neither same as base or counter currency - exchange_rate: Float, is the exchange rate between the account currency and the counter currency. Required for method 2. ''' if JPY_pair == True: #check if a YEN cross and change the multiplier multiplier = 0.01 else: multiplier = 0.0001 #Calc how much to risk acc_value = self.broker.getvalue() cash_risk = acc_value * risk stop_pips_int = abs((price - stop) / multiplier) pip_value = cash_risk / stop_pips_int if method == 1: #pip_value = pip_value * price units = pip_value / multiplier return units elif method == 2: pip_value = pip_value * exchange_rate units = pip_value / multiplier return units else: # is method 0 units = pip_value / multiplier return units |

### Code Commentary

You might have noticed in order to make this function reusable, I added some logic for Japanese pairs and account base currency. This is where the method, exchange_rate and JPY_pair keyword arguments come into play.

For Japanese pairs, the pip value on the pair only goes to 2 decimal places. That affects the multiplier used in the calculations.

The next consideration is account currency. Depending on what your account currency is and which pairs you are trading, it will have an effect on the calculation. Below are examples of how to calculate pip value. I first needed to understand this so I could then work out how to calculate the required position size (units).

**Calculating Pip Value**

- Scenario 1: Where the account currency is the same as the counter currency, (E.g A USD account trading GBP/USD) the calculation is the most simple. It is essentially the value of the trade divided by the multiplier.

pip value = position size * multiplier

pip value = 10,000 * 0.0001

pip value = 1 USD

- Scenario 2: When the account currency is the quote currency. (E.g A GBP account trading GBP/USD) we need to add an extra step.

pip value = (position size / current price) * multiplier

pip value = (10,000 / 1.2950) * 0.0001

pip value = 0.77 GBP

- Scenario 3: Finally, where the account is not in the pair at all (E.g A GBP account trading USD/JPY). Here we need to get the exchange rate between the account currency and the counter currency. Once we have the pip value, we then divide it by the exchange rate (like in the second example but instead using the exchange rate of account currency). This makes it potentially the most tricky to implement in a strategy as you have to monitor an extra currency pair.

pip value = position size * multiplier

pip value = 10,000 * 0.01

pip value = 100 JPY

Pip value = pip value / exchange rate

Pip value = 100 / 142.29

Pip value = 0.70 GBP

**And now to position size**

As I mentioned above, we already know the target pip value we would like to have. It is the amount we are willing to risk divided by the number of pips we have set our stop to. e.g.

pip value = cash to risk / number of pips to stop loss

pip value = $100 / 50

pip value = $2

So if we know our pip value, what we want to figure out is our size….

Units = pip value / multiplier

Units = 2 / 0.0001

Units = 20,000

However, we also need to take into account the base account currency and counter currency. This is not different to when we would when we calculate the pip value. In this case, where we previously divided by the current price or exchange rate, we now multiply. Here is an example.

pip value = pip value * exchange rate

Pip value = 2 * 1.2950

Pip value = 2.59

Units = pip value / multiplier

Units = 2.59 * 0.0001

Units = 25,900

As I mentioned at the start, this took my a while to wrap my little brain around. So if you spot any glaring errors let me know in the comments below.

hi – how can we do something like this on pine script?