///- --package .
coins (test)
test coins: prelude
///- --test static --symbol
:< testing
:| coin =
| GoldCoin
| PlatinumCoin
| CrystalCoin
:= worth (kind : coin) : i32 =
?= kind ?|
| GoldCoin => 1
| PlatinumCoin => 100
| CrystalCoin => 10000
:== purse = { gold : i32; platinum : i32; crystal : i32 }
:= purse gold platinum crystal : purse = { gold platinum crystal }
:= total_gold (held : purse) : i32 =
held::gold * worth GoldCoin + held::platinum * worth PlatinumCoin + held::crystal * worth CrystalCoin
:= fewest_coins (amount : i32) : purse =
:= crystal = amount / worth CrystalCoin
:= after_crystal = amount - crystal * worth CrystalCoin
:= platinum = after_crystal / worth PlatinumCoin
purse (after_crystal - platinum * worth PlatinumCoin) platinum crystal
:| payment =
| Paid : purse
| ShortBy : i32
:= pay (price : i32) (held : purse) : payment =
:= available = total_gold held
? available < price ?> ShortBy (price - available) |: Paid (fewest_coins (available - price))
:= remaining_gold (outcome : payment) : i32 =
?= outcome ?|
| Paid held => total_gold held
| ShortBy _ => -1
fewest_coins_conserves_value (test)
test fewest_coins_conserves_value: passed
///- --test --symbol
///> c
:= ~amount = 1234567i32
fewest_coins amount |> total_gold |> _assert_eq amount
__assert_eq { expected = 1234567 }
fewest_coins_breakdown (test)
test fewest_coins_breakdown: passed
///- --test --symbol
///> c
:= ~amount = 123456i32
:= held = fewest_coins amount
held::crystal |> _assert_eq 12i32
held::platinum |> _assert_eq 34i32
held::gold |> _assert_eq 56i32
__assert_eq { expected = 12 }
__assert_eq { expected = 34 }
__assert_eq { expected = 56 }
paying_conserves_value (test)
test paying_conserves_value: passed
///- --test --symbol
///> c
:= ~price = 2750i32
purse 50 30 1 |> pay price |> remaining_gold |> _assert_eq 10300i32
__assert_eq { expected = 10300 }
paying_too_much_reports_shortfall (test)
test paying_too_much_reports_shortfall: passed
///- --test --symbol
///> c
:= ~price = 20000i32
?= purse 0 0 1 |> pay price ?|
| ShortBy missing => missing |> _assert_eq 10000i32
| Paid _ => _assert_eq 0i32 1i32
__assert_eq { expected = 10000 }
fewest_coins_breakdown_on_gpu (test)
test fewest_coins_breakdown_on_gpu: passed
///- --test --symbol
///> wgsl
:= ~amount = 123456i32
:= held = fewest_coins amount
? held::crystal = 12i32 && held::platinum = 34i32 && held::gold = 56i32 && total_gold held = amount
?> 0i32
|: 1i32