}
3. swap
address tokenA,
3. swap
address to = i < path.length – 2 ? UniswapV2Library.pairFor(factory, output, path[i + 2]) : _to;
address to,
liquidity = Math.min(amount0.mul(_totalSupply) / _reserve0, amount1.mul(_totalSupply) / _reserve1);
liquidity = min((x0/reserve0*totalsupply), (y0/reserve1*totalsupply))
焦点逻辑实此刻UniswapV2Router02.sol中。称为Router,因为Periphery实现了“路由”,支持各个swap之间的毗连。根基上实现了三个成果:1/ add liquidity(增加活动性)2/remove liqudity (抽取活动性) 3/ swap(互换)。
address tokenA,
uint amountOut = amounts[i + 1];
uint deadline
liquidity = Math.sqrt(amount0.mul(amount1)).sub(MINIMUM_LIQUIDITY);
当前的balance是当前的reserve加上注入的活动性的代币数量。
if (_totalSupply == 0) {
address tokenB,
(address token0,) = UniswapV2Library.sortTokens(input, output);
liquidity = sqrt(x0*y0) – min
将代币path[0],转入到生意业务对,数量为amounts[0]。转入代币后,举办真正的swap操纵:
);
活动性liquidity的计较方法在第一次提供活动性时和其他时候稍稍差异。第一次提供活动性的计较公式如下:
Core逻辑实现了单个生意业务对的逻辑。通过UniswapV2Factory可以建设一个个Pair(生意业务池)。每个详细实现逻辑在UniswapV2Pair中。
}
因为在swapExactTokensForTokens的getAmountOut函数已经确定兑换处的金额。所以,先直接转账。
_mint(address(0), MINIMUM_LIQUIDITY); // permanently lock the first MINIMUM_LIQUIDITY tokens
function addLiquidity(
require(amountIn > 0, ‘UniswapV2Library: INSUFFICIENT_INPUT_AMOUNT’);
require(amounts[amounts.length – 1] >= amountOutMin, ‘UniswapV2Router: INSUFFICIENT_OUTPUT_AMOUNT’);
amounts = UniswapV2Library.getAmountsOut(factory, amountIn, path);
amounts是每个路径上的互换后的数量。amounts[amounts.length-1]也就是最后一条路径的输出数量。留意,
if (amount0Out > 0) _safeTransfer(_token0, to, amount0Out); // optimistically transfer tokens
swap函数实现两种代币的兑换。
(uint amount0Out, uint amount1Out) = input == token0 ? (uint(0), amountOut) : (amountOut, uint(0));
Swap整体流程 uint amountAMin,
UniswapV2Library.getAmountsOut的实现(在获取每个生意业务对的reserve信息后,挪用getAmountOut函数):
TransferHelper.safeTransferFrom(
uint deadline
Periphery逻辑
amount0Out, amount1Out, to, new bytes(0)
uint amountOutMin,
uint amount1In = balance1 > _reserve1 – amount1Out ? balance1 – (_reserve1 – amount1Out) : 0;
function removeLiquidity(
) public virtual override ensure(deadline) returns (uint amountA, uint amountB) {
Uniswap智能合约代码由两个github项目构成。一个是core,一个是periphery。
address tokenB,
没想到,Uniswap本年成了热点。在活动性的强需求下,之前的问题仿佛都不存在了。代币能很快活动生意业务起来,让许多项目方变得轻松。可是,也是隐隐以为,之前的问题并没有办理,只是在活动性的需求下掩盖起来。无论如何,Uniswap V2的智能合约代码,照旧要看看的。
确保反推的输入代币数量不小于零。
function swap(uint amount0Out, uint amount1Out, address to, bytes calldata data) external lock {
if (amount1Out > 0) _safeTransfer(_token1, to, amount1Out); // optimistically transfer tokens
Uniswap的代码和逻辑照旧较量清晰的。画个图总结一下,swap的总体流程:
技能长短常有趣的。更有趣的是,区块链技能让生意业务变得更富厚多彩。从中心化生意业务,到去中心化生意业务,再到去中心化AMM。每一种改变都实验办理之前的问题,但自己也不是完美的。也值得一提的,每一点点进步都很是不容易。有种不积跬步,无以至千里的感受。
个中min是10^3。也就是说,第一次提供活动性是有最小活动性要求的。其他提供活动性的计较公式如下:
require(reserveIn > 0 && reserveOut > 0, ‘UniswapV2Library: INSUFFICIENT_LIQUIDITY’);
}
) external virtual override ensure(deadline) returns (uint amountA, uint amountB, uint liquidity)
uint amountAMin,
uint _totalSupply = totalSupply; // gas savings, must be defined here since totalSupply can update in _mintFee
2. burn
道理较量简朴,针对每一条路径,挪用生意业务对的swap操纵。
uint amountBDesired,
uint amountBMin,
function burn(address to) external lock returns (uint amount0, uint amount1) {
function _swap(uint[] memory amounts, address[] memory path, address _to) internal virtual {
for (uint i; i < path.length – 1; i++) {
uint amountIn,
郑重声明:本文版权归原作者所有,转载文章仅为传播更多信息之目的,如作者信息标记有误,请第一时间联系我们修改或删除,多谢。