解释 Uniswap V3 兑换函数

本文详细解释了 Uniswap V3 路由器的四个核心交易函数:exactInputSingle、exactInput、exactOutputSingle 和 exactOutput。针对每种函数,文章分析了其用途、签名、参数以及实际应用场景,同时强调了在进行交易时需要注意的安全问题,例如防止抢跑交易和滑点攻击。

Uniswap V3 交换函数

Uniswap V3 是以太坊上最先进的 AMM(自动化做市商),为 ERC20 代币提供高效的链上交换。当从智能合约中使用 Uniswap 时,你需要与路由器接口(特别是 ISwapRouter)交互,以通过编程方式执行交换。

本博客将分解每个主要的交换函数(及其参数!),以便你可以为你的场景选择合适的工具并构建强大的 DeFi 集成。

四个核心 Uniswap V3 交换方法

Uniswap V3 的 ISwapRouter 公开了四种主要的代币交换方式:

  1. exactInputSingle
  2. exactInput
  3. exactOutputSingle
  4. exactOutput

让我们详细解释每一个。

1. exactInputSingle: 单个池,精确输入量

目的:

交换已知数量的 tokenIn 以获得尽可能多tokenOut,所有这些都通过单个 Uniswap V3 池。

签名:

function exactInputSingle(ExactInputSingleParams calldata params) external payable returns (uint256 amountOut);

参数(打包在结构体中):

  • tokenIn: 输入代币的地址(例如,DAI)。
  • tokenOut: 输出代币的地址(例如,WETH)。
  • fee: 池费用(500、3000 或 10000 分别对应 0.05%、0.3%、1%)。
  • recipient: 将输出代币发送到哪里。
  • amountIn: 要交换的 tokenIn 的固定数量。
  • amountOutMinimum: 你将接受的 tokenOut 的最小数量(防止抢跑/滑点)。
  • sqrtPriceLimitX96: 可选。为交换设置价格边界(0 表示无限制)。

实践中的用法:

简单的交换(DAI↔WETH、USDC↔USDT 等),无需通过多个交易对进行路由。

示例场景: 交换正好 1000 DAI 以接收尽可能多的 WETH。

2. exactInput: 多跳,精确输入量

目的:

交换已知数量的 tokenIn 以获得尽可能多的最终 tokenOut,可能会通过多个池进行路由(多跳交换)。

签名:

function exactInput(ExactInputParams calldata params) external payable returns (uint256 amountOut);

参数(在结构体中):

  • path: 字节数据,用于编码代币和费用序列,例如 tokenA, feeAB, tokenB, feeBC, tokenC
  • recipient: 谁接收到输出代币。
  • amountIn: 整个路由的 tokenIn 的固定数量。
  • amountOutMinimum: 最小可接受输出。

路径示例 (DAI → WETH → WBTC):

abi.encodePacked(DAI, uint24(3000), WETH, uint24(3000), WBTC)

实践中的用法:

对于单个池中未直接支持的交换(例如,DAI→WETH→WBTC),或用于查找通过中间资产的最佳路线。

3. exactOutputSingle: 单个池,精确输出量

目的:

接收精确数量的 tokenOut,同时花费尽可能少tokenIn,通过单个 Uniswap 池。

签名:

function exactOutputSingle(ExactOutputSingleParams calldata params) external payable returns (uint256 amountIn);

参数:

  • tokenIn: 输入代币的地址。
  • tokenOut: 输出代币的地址。
  • fee: 池费用。
  • recipient: 输出代币的接收者。
  • amountOut: 所需的,精确的 tokenOut 输出量。
  • amountInMaximum: 你允许花费的最多输入代币(滑点保护)。
  • sqrtPriceLimitX96: 可选的价格边界(设置为 0 表示无限制)。

实践中的用法:

你需要正好例如 1 ETH,但想要花费尽可能少的 DAI,并且你愿意限制总输入量,因为价格影响或滑点。

4. exactOutput: 多跳,精确输出量

目的:

通过多个池接收精确数量的 tokenOut,花费尽可能少的输入(但不超过你设置的最大值)。

签名:

function exactOutput(ExactOutputParams calldata params) external payable returns (uint256 amountIn);

参数:

  • path: 字节,用于编码从输出到输入的交换路线(即,与 exactInput 相比是反向的!)。
  • recipient: 谁获得输出。
  • amountOut: 你想要的精确的输出代币数量。
  • amountInMaximum: 你愿意花费的最大输入代币数量。

WBTC(输出)← WETH ← DAI(输入)的示例路径:

abi.encodePacked(WBTC, uint24(3000), WETH, uint24(3000), DAI)

(注意:多跳 exactOutput 路径是反向的!)

实践中的用法:

对于需要保证输出代币中特定支付金额的用例(例如,对于 NFT 或固定价格购买),优化你花费的少量输入非常有用。

关键设计模式和安全性

  • 始终填写 amountOutMinimum/amountInMaximum 以防止抢跑和三明治攻击。
  • 为你提供的任何代币批准路由合约(IERC20(tokenIn).approve(...))。
  • 除非你想强制执行严格的价格边界,否则 sqrtPriceLimitX96 几乎总是安全的设置为 0。
  • 对于多跳路线,请确保每个池(每个跳)都有流动性!

结论

Uniswap V3 的路由器为你提供了巨大的灵活性:

  • 使用 exactInputSingle 进行简单,单跳最大输出交换。
  • 使用 exactInput 通过多个池进行复杂交换,并具有固定的输入。
  • 当你确切知道自己想要接收什么并想限制你的支出时,请使用 exactOutputSingleexactOutput

通过这种理解,你可以将高效,强大的 DeFi 交换集成到你自己的合约和 dApp 中!

进一步阅读:

祝你交换愉快。

  • 原文链接: coinsbench.com/uniswap-v...
  • 登链社区 AI 助手,为大家转译优秀英文文章,如有翻译不通的地方,还请包涵~
点赞 0
收藏 0
分享
本文参与登链社区写作激励计划 ,好文好收益,欢迎正在阅读的你也加入。

0 条评论

请先 登录 后评论
CoinsBench
CoinsBench
https://coinsbench.com/