2个版本

0.1.1 2019年11月8日
0.1.0 2019年10月31日

#7 in #指数

MPL-2.0 许可证

30KB
565

Monet

Build Status MPL-2.0 Licensed Crates.io Docs

处理货币转换和常见操作(加法、减法、乘法、除法)。

工作原理

它定义了一些基本类型

  • CurrencyAmounti128,正如其名,用于存储金额。
  • CurrencyCode[u8; 3] 的包装器,可以从 / 转换为 &str
  • Money 是最重要的类型。Money 包含一个 currency_code 和一个 amount。它用于存储货币并执行操作。可以通过提供 Rates 将其转换为另一个货币代码。
  • Rates 是一个 HashMap 的包装器。可以从这样的预定义映射或 从外部源(如网站)中填充(尚未实现,待办事项:实现)构建。
  • Exponent 存在是因为这里没有涉及 float。它有两个字段:amountexponent。它的十进制值是 amount / (10).pow(exponent)

危险

即使这个库也不免于精度损失。例如,一个 Exponent 的金额可能会被其指数截断。此外,在转换货币时可能会发生错误。

示例

相加两个相同类型的 Money


use monet::{Money, CurrencyAmount, Rates, Operation};
use std::convert::TryInto;

// Custom rates.
let map = vec![("USD", 1_000_000)].into_iter()
    .map(|(code, worth)| (code.try_into().unwrap(), worth.into())
    .collect();
let rates = Rates::with_rates(map);

let money_owned = Money::with_str_code(CurrencyAmount::with_unit(2), "USD").unwrap();
let money_paid = Money::with_str_code(CurrencyAmount::with_unit(1), "USD").unwrap();

let remaining = (money_owned - money_paid).execute(&rates);

assert_eq!(remaining, Money::with_str_code(CurrencyAmount::with_unit(1), "USD"));
assert_eq!(remaining, Money::with_str_code(1_000_000.into(), "USD"));


相加两个不同类型的 Money


use monet::{Money, CurrencyAmount, Rates, Operation};
use std::convert::TryInto;

// Custom rates.
let map = vec![
    ("USD", 1_000_000),
    ("CHF", 1_100_000),
].into_iter()
    .map(|(code, worth)| (code.try_into().unwrap(), worth.into())
    .collect();

let rates = Rates::with_rates(map);

let money_one = Money::with_str_code(1_000_000.into(), "CHF").unwrap();
let money_two = Money::with_str_code(1_100_000.into(), "USD").unwrap();

// Note: sum has currency code "CHF": when summing,
// the currency code of the first money is used
let sum = (money_one + money_two).execute(&rates);

assert_eq!(remaining, Money::with_str_code(2_000_000.into(), "CHF"));

链式操作


use monet::{Money, CurrencyAmount, Rates, Operation};
use std::convert::TryInto;

// Custom rates.
let map = vec![
    ("USD", 1_000_000),
    ("CHF", 1_100_000),
].into_iter()
    .map(|(code, worth)| (code.try_into().unwrap(), worth.into())
    .collect();

let rates = Rates::with_rates(map);

let money_one = Money::with_str_code(1_000_000.into(), "CHF").unwrap();
let money_two = Money::with_str_code(1_100_000.into(), "USD").unwrap();
let money_three = Money::with_str_code(2_000_000.into(), "CHF").unwrap();

// Note: sum has currency code "CHF"
let sum = (money_one + money_two - money_three).execute(&rates);

assert_eq!(remaining, Money::with_str_code(0.into(), "CHF"));

依赖关系

~205KB