MultiversXDeFi金融数学技能Skill mvx_defi_math

这个技能用于MultiversX区块链DeFi项目中的金融数学计算,包括精度管理、半上舍入、安全重缩放和百分比计算等,确保交易和协议的安全性与准确性。关键词:DeFi, 金融数学, 精度管理, 舍入, 区块链, 智能合约, 风险控制。

DeFi 0 次安装 0 次浏览 更新于 3/21/2026

名称: mvx_defi_math 描述: MultiversX DeFi 的金融数学 — 精度管理、半上舍入、安全重缩放、百分比计算。

MultiversX DeFi 数学模式

精度级别

级别 小数位数 使用场景
BPS (4) 10,000 = 100% 费用,简单百分比
PPM (6) 1,000,000 = 100% 细粒度百分比
WAD (18) 1e18 = 1.0 代币数量,价格
RAY (27) 1e27 = 1.0 利息指数,复利,高精度数学
pub const BPS: u64 = 10_000;
pub const PPM: u64 = 1_000_000;
pub const WAD: u128 = 1_000_000_000_000_000_000;
pub const RAY: u128 = 1_000_000_000_000_000_000_000_000_000;

规则: 使用避免舍入误差的最低精度。中间计算使用比最终结果更高的精度。

半上舍入

标准的 ManagedDecimal 截断 → 系统性价值损失 → 可被利用。

乘法

fn mul_half_up(&self, a: &ManagedDecimal<Self::Api, NumDecimals>, b: &ManagedDecimal<Self::Api, NumDecimals>, precision: NumDecimals) -> ManagedDecimal<Self::Api, NumDecimals> {
    let product = a.rescale(precision).into_raw_units() * b.rescale(precision).into_raw_units();
    let scaled = BigUint::from(10u64).pow(precision as u32);
    let rounded = (product + &scaled / 2u64) / scaled;
    self.to_decimal(rounded, precision)
}

除法

fn div_half_up(&self, a: &ManagedDecimal<Self::Api, NumDecimals>, b: &ManagedDecimal<Self::Api, NumDecimals>, precision: NumDecimals) -> ManagedDecimal<Self::Api, NumDecimals> {
    let scaled = BigUint::from(10u64).pow(precision as u32);
    let numerator = a.rescale(precision).into_raw_units() * &scaled;
    let denominator = b.rescale(precision).into_raw_units();
    let rounded = (numerator + &denominator / 2u64) / denominator;
    self.to_decimal(rounded, precision)
}

安全重缩放

fn rescale_half_up(&self, value: &ManagedDecimal<Self::Api, NumDecimals>, new_precision: NumDecimals) -> ManagedDecimal<Self::Api, NumDecimals> {
    let old = value.scale();
    if new_precision >= old { return value.rescale(new_precision); }
    let factor = BigUint::from(10u64).pow((old - new_precision) as u32);
    ManagedDecimal::from_raw_units((value.into_raw_units() + &factor / 2u64) / factor, new_precision)
}

百分比计算

框架内置: proportion()

// 首选 — 使用框架中的 BigUint::proportion(part, total)
pub const PERCENT_BASE_POINTS: u64 = 100_000;  // 100% = 100_000
let fee = amount.proportion(fee_percent, PERCENT_BASE_POINTS);

手动 BPS / PPM

pub fn apply_bps(amount: &BigUint, bps: u64) -> BigUint { (amount * bps) / 10_000u64 }
pub fn apply_ppm(amount: &BigUint, ppm: u32) -> BigUint { (amount * ppm) / 1_000_000u64 }

舍入攻击向量

攻击 缓解措施
粉尘存款以窃取舍入 在缩放金额上使用半上舍入
重复小操作 最小金额 + 在指数上使用半上舍入
转换中的精度损失 中间数学使用 RAY 精度
费用计算中的截断 向上舍入费用(协议优势)

反模式

  • 混合精度而不重缩放
  • 截断除法用于费用(应使用向上舍入除法)
  • 中间结果在低精度(计算时使用 RAY,最后降精度)

领域应用

  • 借贷: 利息模型,复利,利用率 — RAY 精度
  • DEX: 价格影响,LP 份额 — WAD 精度,使用半上舍入
  • 质押: 奖励分配,份额比率 — RAY 指数
  • 保险库: 费用计算,收益 — BPS 费用,使用向上舍入除法