Rust 中 Wrapping(Uint) 的余数等简单操作

问题描述 投票:0回答:1

我正在使用板条箱 crypto_bigint 来操作大数字,但文档确实让我感到困惑。 所以显然你需要决定是否要检查或包装你的操作,我需要进行 bit_and 操作,并且由于某种原因不可能检查 Uint,所以我选择了包装。

我几乎无法执行加法 a 和 以及右移。

我想得到一些剩余的。所以我尝试简单地执行 %,然后编译器告诉我 rem 方法没有类型 crypto-bigint::Wrapping 的实现,但我可以看到它确实存在于 doc 中,并且相应的类型实现了 Traits Rem。

这是一个会产生大量错误的示例

use crypto_bigint::{Wrapping, U2048}; //apparently not the correct imports

pub fn mod_exp(
    base: Wrapping<U2048>,
    exp: Wrapping<U2048>,
    modulus: Wrapping<U2048>,
) -> Wrapping<U2048> {
    let one = Wrapping(U2048::ONE);
    let mut result = Wrapping(U2048::ONE);
    let mut base = base % modulus; // Ensure base is reduced modulo
    let mut exp = exp;

    while exp > Wrapping(U2048::ZERO) {
        if exp & one == one {
            result = (result * base).rem(modulus);
        }
        exp = Wrapping(exp.0.shr(1_usize));
        base = (base * base).rem(modulus); // Modular square
    }
    result
}
error[E0277]: cannot calculate the remainder of `crypto_bigint::Wrapping<Uint<32>>` divided by `crypto_bigint::Wrapping<Uint<32>>`
  --> src\lib.rs:10:25
   |
10 |     let mut base = base % modulus; // Ensure base is reduced modulo
   |                         ^ no implementation for `crypto_bigint::Wrapping<Uint<32>> % crypto_bigint::Wrapping<Uint<32>>`
   |
   = help: the trait `Rem` is not implemented for `crypto_bigint::Wrapping<Uint<32>>`
   = help: the following other types implement trait `Rem<Rhs>`:
             `&crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<&crypto_bigint::NonZero<Limb>>`
             `&crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<&crypto_bigint::NonZero<Uint<LIMBS>>>`
             `&crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<crypto_bigint::NonZero<Limb>>`
             `&crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<crypto_bigint::NonZero<Uint<LIMBS>>>`
             `crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<&crypto_bigint::NonZero<Limb>>`
             `crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<&crypto_bigint::NonZero<Uint<LIMBS>>>`
             `crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<crypto_bigint::NonZero<Limb>>`
             `crypto_bigint::Wrapping<Uint<LIMBS>>` implements `Rem<crypto_bigint::NonZero<Uint<LIMBS>>>`

这可能只是一个糟糕的导入,但我不知道该怎么做。我尝试了编译器建议的“解决方案”,但它产生的问题比解决的问题还要多。例如,我尝试使用“as Rem

>>”将 
Wrapping(U2048)
 转换为 
Rem<NonZero<Uint<32>>>,但随后我需要定义输出类型,而我使用的语法不起作用。

rust bigint
1个回答
0
投票

看起来你需要使用

NonZero
:

use crypto_bigint::{NonZero, Wrapping, U2048};

pub fn mod_exp<const LIMBS: usize>(
    base: Wrapping<U2048>,
    exp: Wrapping<U2048>,
    modulus: NonZero<U2048>,
) -> Wrapping<U2048> {
    let one = Wrapping(U2048::ONE);
    let mut result = Wrapping(U2048::ONE);
    let mut base = Wrapping(base.0.rem(&modulus)); // Ensure base is reduced modulo
    let mut exp = exp;

    while exp > Wrapping(U2048::ZERO) {
        if exp & one == one {
            result = Wrapping((result * base).0.rem(&modulus));
        }
        exp = Wrapping(exp.0.shr(1_usize));
        base = Wrapping((base * base).0.rem(&modulus)); // Modular square
    }
    result
}
© www.soinside.com 2019 - 2024. All rights reserved.