Tips & Tricks
Calculating a proportional VWAP for a quantity when given a list of prices and smaller quantities.
q)prices: 1.2 1.3 1.4 1.5 1.6 1.7
q)quantities: 1000 2000 3000 4000 5000 6000
q)prices,'quantities
1.2 1000
1.3 2000
1.4 3000
1.5 4000
1.6 5000
1.7 6000
q)/ find the VWAP price for a quantity of 11000
q)deltas[11000 & sums quantities] wavg prices
1.418182
This is a neat solution. First, get the running sum of the quantities and at each point take the maximum of the running sum and the final number 11000. This gives us the following list:
q)n&sums quantities
1000 3000 6000 10000 11000 11000
This helps us to find at which point we reach our target number (at index 4 or the 5000 quantity 'level'), but we don't want this to be as shown. Rather than the final numbers being our target number, we need them to represent the quantity taken from that level. So we can use deltas:
q)deltas[n&sums quantities]
1000 2000 3000 4000 1000 0
This is exactly what we want - the quantity taken from each 'level' with only 1000 taken from the 5000 level and 0 taken from the 6000 level. Then it's simply a matter of taking a 'wavg' of these and the bids (the 0 level will essentially be ignored).
This may be useful in the FX world where prices are regularly quoted in terms of quantity layers, and frequently these are received in one list. Take the following example:
q)fxMarketData:([] time:2024.11.08D01:30:00 2024.11.08D01:30:00;bid:(1.1 1.2 1.3; 1.1 1.15); bidSize:(1000 2000 3000;500 400))
q)fxMarketData
time bid bidSize
--------------------------------------------------------
2024.11.08D01:30:00.000000000 1.1 1.2 1.3 1000 2000 3000
2024.11.08D01:30:00.000000000 1.1 1.15 500 400
q)/All bid quotes are active. Find the best price available for a quantity of 5500
q)exec vwap:deltas[5500&sums bidSize] wavg bid from `bid xdesc ungroup fxMarketData
vwap| 1.249091
Credit to the answer from 'matthew.j' on this stackoverflow question.