1 个不稳定版本
0.5.9 | 2023年10月25日 |
---|
313 在 数学 中排名
2,106 每月下载量
在 22 个 crates 中使用 (2 直接))
720KB
14K SLoC
substrate 的定点数
此 crate 是从 fixed = 0.5.4
端口移植的。它已被适配以在 substrate 运行时中使用。此外,还添加了超越函数(对数、指数、幂、三角函数)。
请查阅 我们的 encointer-js 库 了解如何为 JavaScript UI 解析定点值。
[substrate-fixed crate] 提供定点数。
FixedI8
和FixedU8
是 8 位定点数。FixedI16
和FixedU16
是 16 位定点数。FixedI32
和FixedU32
是 32 位定点数。FixedI64
和FixedU64
是 64 位定点数。FixedI128
和FixedU128
是 128 位定点数。
这些类型可以有 Frac
分数位,其中 0 ≤ Frac
≤ n,而 n 是总位数。当 Frac
= 0 时,定点数的行为像 n 位整数。当 Frac
= n 时,有符号数 x 的值在 −0.5 ≤ x < 0.5 的范围内,而对于无符号数,则在 0 ≤ x < 1 的范围内。
目前使用 typenum crate 来计算分数位 Frac
;计划在 Rust 编译器支持时转向 const generics。
主要特性包括
- 支持高达 128 位的定点数表示。
- 定点数与数值原语之间的转换。
- 定点数与数值原语之间的比较。
- 从十进制、二进制、八进制和十六进制字符串进行解析。
- 以十进制、二进制、八进制和十六进制显示。
- 算术和逻辑操作。
支持的转换包括以下情况。
- 使用
From
和Into
提供定点数与数值原语之间的可靠无损转换。这些转换永远不会失败(可靠)且不会丢失任何位(无损)。 - 使用
LossyFrom
和LossyInto
特性提供定点数与数值原语之间的可靠有损转换。源可以比目标拥有更多的分数位。 - 使用
FromFixed
和ToFixed
特性,或者使用from_num
和to_num
方法以及它们的校验版本,提供定点数与数值原语之间的校验转换。 - 定点数可以使用
FromStr
从十进制字符串进行解析,以及使用from_str_binary
、from_str_octal
和from_str_hex
方法从二进制、八进制和十六进制字符串进行解析。结果四舍五入到最接近的值,如果相等则四舍五入到偶数。 - 定点数可以使用
Display
、Binary
、Octal
、LowerHex
和UpperHex
转换为字符串。输出四舍五入到最接近的值,如果相等则四舍五入到偶数。
上游版本
有关其他版本的信息可以在 RELEASES.md 中找到。
快速示例
use substrate_fixed::types::I20F12;
// 19/3 = 6 1/3
let six_and_third = I20F12::from_num(19) / 3;
// four decimal digits for 12 binary digits
assert_eq!(six_and_third.to_string(), "6.3333");
// find the ceil and convert to i32
assert_eq!(six_and_third.ceil().to_num::<i32>(), 7);
// we can also compare directly to integers
assert_eq!(six_and_third.ceil(), 7);
类型 I20F12
是一个32位固定点有符号数,具有20位整数位和12位小数位。它是 FixedI32<U12>
的别名。其无符号对应类型为 U20F12
。为所有整数位和小数位总和为8、16、32、64或128位的组合提供了别名。
use substrate_fixed::types::{I4F4, I4F12};
// −8 ≤ I4F4 < 8 with steps of 1/16 (~0.06)
let a = I4F4::from_num(1);
// multiplication and division by integers are possible
let ans1 = a / 5 * 17;
// 1 / 5 × 17 = 3 2/5 (3.4), but we get 3 3/16 (~3.2)
assert_eq!(ans1, I4F4::from_bits((3 << 4) + 3));
assert_eq!(ans1.to_string(), "3.2");
// −8 ≤ I4F12 < 8 with steps of 1/4096 (~0.0002)
let wider_a = I4F12::from(a);
let wider_ans = wider_a / 5 * 17;
let ans2 = I4F4::from_num(wider_ans);
// now the answer is the much closer 3 6/16 (~3.4)
assert_eq!(ans2, I4F4::from_bits((3 << 4) + 6));
assert_eq!(ans2.to_string(), "3.4");
第二个例子展示了精度和转换问题。变量 a
的低精度意味着 a / 5
等于 3/16 而不是 1/5,导致结果 ans1
= 3 3/16 (~3.2) 不准确。提高精度后,我们得到 wider_a / 5
等于 819/4096,导致更准确的中间结果 wider_ans
= 3 1635/4096。当我们将其转换回四位小数时,我们得到 ans2
= 3 6/16 (~3.4)。
注意,我们可以使用 From
将 I4F4
转换为 I4F12
,因为目标类型具有相同数量的整数位和更多的小数位。从 I4F12
转换到 I4F4
不能使用 From
,因为我们有更少的小数位,所以使用 from_num
代替。
使用 substrate-fixed 包
substrate-fixed 包目前尚未在 crates.io 上提供。要在您的包中使用它,请在 Cargo.toml 中将其添加为 git 依赖项。
[dependencies.fixed]
default-features = false
git = "https://github.com/encointer/substrate-fixed"
package = "substrate-fixed"
substrate-fixed 包需要 rustc 版本 1.39.0 或更高。
可选特性
fixed 包有四个可选特性
az
,默认禁用。这实现了由 az 包 提供的铸件特性。f16
,默认禁用。这提供了与f16
和bf16
的转换。此特性需要 half 包。serde
,默认禁用。这为固定点类型提供了序列化支持。此特性需要 serde 包。std
,默认禁用。这是在no_std
下不可用的特性:目前是ParseFixedError
的Error
特性的实现。
要启用功能,您可以将依赖项添加到如下所示的 Cargo.toml 文件中。
[dependencies.fixed]
default-features = false
git = "https://github.com/encointer/substrate-fixed"
package = "substrate-fixed"
features = ["f16", "serde"]
许可证
此软件包是免费软件:您可以在以下任一许可证的条款下重新分发和/或修改它
任选其一。
贡献
除非您明确声明,否则根据 Apache License, Version 2.0 定义,您有意提交以包含在本作品中的任何贡献,应按上述方式双许可,不附加任何额外条款或条件。
依赖项
~3.5MB
~81K SLoC