---
# System prepended metadata

title: Uniswap V3 Special Case (V2) DEPRECATED

---

# Uniswap V3 Special Case (V2) DEPRECATED

This document is very much a work in progress with lots of TODOs.

## Curve Equations
Let `virtual_L = v_L = f L / sqrt( (1/slo - 1/shi) * (shi - slo) )`

`p in (lo, hi)`
`(x + virtual_L slo)(y + virtual_L / shi) = ( virtual_L + (1-f)L )^2`

`p < lo`
`(x - virtual_L (shi - slo)) y = (1 - f)^2 L^2`

`p > hi`
`x (y - virtual_L (1 / slo - 1 / shi) ) = (1 - f)^2 L^2`

## Difference Equations
Given `(x,y)`, we can derive `L` and from there derive the difference equations.

In all of the following, `V' := f / sqrt((1/slo - 1/shi) * (shi - slo))`

### Find which zone `(x,y)` is in

Based on `(x,y)` you can tell your price is in `(lo, hi)`, `p < lo`, or `p > hi`.

TODO : calculate the price of a given `(x,y)`.

### `p \in (lo,hi)`
`L` is the root of the following polynomial:

`(V'^2 slo / shi - (V' + (1-f))^2) L^2 + `
`(xV'/shi + y V' slo) L +  xy`

so we're simulating a curve of the form `xy = k` where:
`k = f^2 * L^2 / ((1/slo - 1/shi)(shi - slo))`.

### `p < lo`
`L` is the root of the following polynomial:

`(1-f)^2 L^2 + (V' y (shi - slo)) L - xy`

and we're simulating the curve `xy = k` where `k = (1-f)^2 L^2`


### `p > hi`
`L` is the root of the following polynomial:

`(1-f)^2 L^2 + (V' x (1/slo - 1/shi)) L - xy`

and we're simulating the curve `xy = k` with `k = (1-f)^2 L^2`

### Difference Equations

For trades that don't cross a tick, calculate the trade using `k` from above.

Given `∆x`: `∆y = k / (x + ∆x) - y`
Given `∆y`: `∆x = k / (y + ∆y) - x`

If the trade exceeds the tick then separate the trade recursively into two trades, where the second is across the tick and the first trade moves the price to `lo` or `hi`.


## The Virtual Isoutility Curve 

The virtual isoutility curve is meant to optimise capital efficiency by simulating the constant product market maker such that, between two prices, `p0` and `p1`, all liquidity provided for that range gets used.

We would like to derive the constant `k` for a given amount of liquidity such that between prices `p0` and `p1`, all provided liquidity is used efficiently. In other words, if `p = p0`, `real_quantity_token1 = 0`, and if `p = p1`, `real_quantity_token2 = 0`. (`real_quantity` as opposed to `synthetic_quantity` which obeys the rule that `x * y = k`.)

### Deriving `∆x` and `∆y` between prices `p0` and `p1`
For an arbitrary `k`, and prices `0 < p0 < p1` we will derive the formula to find the quantity of `token1` needed (`∆y`) to move the price of `token0` (in terms of `token1`) from `p0` to `p1`.

We have the initial conditions that `x * y = k` and `y / x = p0`. The end conditions are that `x * y = k` and `y / x = p1`. We can derive the initial values of `x` and `y` (*i.e.* quantities of `token0` and `token1`) as follows:

`y / x = p0 => y = x * p0 => (x ** 2) p0 = k => x = sqrt(k / p0)`

We can derive the initial quantity of `y` similarly:

`y = x * p0 = x * sqrt(k / p0) = sqrt(k * p0)`

Likewise we have the end conditions that:

`x = sqrt(k / p1)` and `y = sqrt(k * p1)`

Thus moving from `p = p0` to `p = p1` gives us:

`∆x = sqrt(k / p1) - sqrt(k / p0)` 
`∆y = sqrt(k * p1) - sqrt(k * p0)`

Note that `∆x < 0` and `∆y > 0`.

### Deriving the Virtual Isoutility Curve 

To find the virtual isoutility curve for concentrated liquidity we need `p0`, `p1`, and `k`. In our case we have `p0` and `p1` given, and we have the amount of liquidity concentrated in this price range, but we don't have access to `k` a priori.

Suppose we want to conentrate `100 token1` worth of liquidity between prices `p0` and `p1`. (Actually depositing `100 token1` worth of tokens is only possible if `p > p1` and the concentrated pool is composed entirely of `token1`. In practice, one has to deposit some amount of both tokens.)

We can use our formulae derived above to derive `k`. We know that it requires `100 token1` to traverse the price range `[p0, p1]`. Thus `∆y = 100` and we have:

`100 = sqrt(k) * (sqrt(p1) - sqrt(p0))`
` => k = (100 / (sqrt(p1) - sqrt(p0))) ** 2`

and we have the virtual isoutility curve given by `x * y = k`.

## Continuity of the Isoutility Curve
TODO : This problem needs a bit of clarifying


## Adding/Removing Liquidity
TODO : Add precise details and clarify the following idea:

When adding liquidity, if the price is outside of the band, then liquidity can be added as follows: 20% gets added in proportion to the price `y/x`; 80% gets added purely in `token1` if the price is above the higher tick `p1`, and purely in `token0` if price is below the lower tick `p0`.

If the price is inside the band, then 20% gets added proportional to the price `y/x`. The 80% pool is more complex: you should calculate the quantity of `token1` needed to move the price from `p0` to the current price; add liquidity in proportion to that. (TODO : This idea is not quite complete.)


## Trading
### Within the Band
TODO: Complete these thoughts and add more detail.

To calculate the full (the 80% virtual plus the real 20%), we can calculate the virtual curve and add to it the "real" (20%) curve.

You can calculate the total quantity of tokens being traded using the total (virtual and real) isoutility curve. Based on the price change, you can calculate how many of those tokens came out of the 20% pool; the rest should come out of the 80% pool. TODO: Verify (and prove) these match up correctly.

### Outside of the Band 
Trading outside the band is straightforward. Simply use the curve `x * y = k` with `k` being the unconcentrated liquidity.

### Crossing a Tick
Follow the flow chart (with maximum two iterations). 

![](https://i.imgur.com/mxpb1vF.png)

That is, if the trade causes a price movement past a ticker, calculate the trade up to the ticker, and then continue with the trade after the next tick. As there are only two ticks, this can iterate at maximum 3 times.

Fees are calculated as if it were two (up to three) separate trades. (See Fees sections below.)


## LP Tokens
TODO: 
These are fungible. 

One LP token should represent one unit of liquidity `L`, with `L = k ** 2`. TODO : Calculate precisely what this means in the case of concentrated liquidity.

## Fees 
Fees can be reinvested in the pool since LP tokens are fungible, increasing the value of each LP token. Fees should be reinvested in line with the "Adding Liquidity" section.


