Fix rounding functions and tests

This commit is contained in:
NicklasXYZ 2024-08-12 22:55:26 +02:00
parent 42c4ae114d
commit 7ecaad5be2
3 changed files with 116 additions and 134 deletions

View file

@ -112,7 +112,7 @@ import gleam_community/maths/elementary
/// </a> /// </a>
/// </div> /// </div>
/// ///
pub fn ceiling(x: Float, digits: option.Option(Int)) -> Result(Float, String) { pub fn ceiling(x: Float, digits: option.Option(Int)) -> Float {
round(x, digits, option.Some(RoundUp)) round(x, digits, option.Some(RoundUp))
} }
@ -167,7 +167,7 @@ pub fn ceiling(x: Float, digits: option.Option(Int)) -> Result(Float, String) {
/// </a> /// </a>
/// </div> /// </div>
/// ///
pub fn floor(x: Float, digits: option.Option(Int)) -> Result(Float, String) { pub fn floor(x: Float, digits: option.Option(Int)) -> Float {
round(x, digits, option.Some(RoundDown)) round(x, digits, option.Some(RoundDown))
} }
@ -222,7 +222,7 @@ pub fn floor(x: Float, digits: option.Option(Int)) -> Result(Float, String) {
/// </a> /// </a>
/// </div> /// </div>
/// ///
pub fn truncate(x: Float, digits: option.Option(Int)) -> Result(Float, String) { pub fn truncate(x: Float, digits: option.Option(Int)) -> Float {
round(x, digits, option.Some(RoundToZero)) round(x, digits, option.Some(RoundToZero))
} }
@ -360,7 +360,7 @@ pub fn round(
x: Float, x: Float,
digits: option.Option(Int), digits: option.Option(Int),
mode: option.Option(RoundingMode), mode: option.Option(RoundingMode),
) -> Result(Float, String) { ) -> Float {
case digits { case digits {
option.Some(a) -> { option.Some(a) -> {
let assert Ok(p) = elementary.power(10.0, conversion.int_to_float(a)) let assert Ok(p) = elementary.power(10.0, conversion.int_to_float(a))
@ -381,35 +381,17 @@ pub type RoundingMode {
RoundUp RoundUp
} }
fn do_round( fn do_round(p: Float, x: Float, mode: option.Option(RoundingMode)) -> Float {
p: Float,
x: Float,
mode: option.Option(RoundingMode),
) -> Result(Float, String) {
case mode { case mode {
// Determine the rounding mode // Determine the rounding mode
option.Some(RoundNearest) -> option.Some(RoundNearest) -> round_to_nearest(p, x)
round_to_nearest(p, x) option.Some(RoundTiesAway) -> round_ties_away(p, x)
|> Ok option.Some(RoundTiesUp) -> round_ties_up(p, x)
option.Some(RoundTiesAway) -> option.Some(RoundToZero) -> round_to_zero(p, x)
round_ties_away(p, x) option.Some(RoundDown) -> round_down(p, x)
|> Ok option.Some(RoundUp) -> round_up(p, x)
option.Some(RoundTiesUp) ->
round_ties_up(p, x)
|> Ok
option.Some(RoundToZero) ->
round_to_zero(p, x)
|> Ok
option.Some(RoundDown) ->
round_down(p, x)
|> Ok
option.Some(RoundUp) ->
round_up(p, x)
|> Ok
// Otherwise, use the default rounding mode // Otherwise, use the default rounding mode
option.None -> option.None -> round_to_nearest(p, x)
round_to_nearest(p, x)
|> Ok
} }
} }

View file

@ -247,9 +247,9 @@ fn do_ceiling(a: Float) -> Float
pub fn is_power(x: Int, y: Int) -> Bool { pub fn is_power(x: Int, y: Int) -> Bool {
let assert Ok(value) = let assert Ok(value) =
elementary.logarithm(int.to_float(x), option.Some(int.to_float(y))) elementary.logarithm(int.to_float(x), option.Some(int.to_float(y)))
let assert Ok(truncated) = piecewise.truncate(value, option.Some(0)) let truncated = piecewise.truncate(value, option.Some(0))
let rem = value -. truncated let remainder = value -. truncated
rem == 0.0 remainder == 0.0
} }
/// <div style="text-align: right;"> /// <div style="text-align: right;">

View file

@ -7,308 +7,308 @@ import gleeunit/should
pub fn float_ceiling_test() { pub fn float_ceiling_test() {
// Round 3. digit AFTER decimal point // Round 3. digit AFTER decimal point
piecewise.ceiling(12.0654, option.Some(3)) piecewise.ceiling(12.0654, option.Some(3))
|> should.equal(Ok(12.066)) |> should.equal(12.066)
// Round 2. digit AFTER decimal point // Round 2. digit AFTER decimal point
piecewise.ceiling(12.0654, option.Some(2)) piecewise.ceiling(12.0654, option.Some(2))
|> should.equal(Ok(12.07)) |> should.equal(12.07)
// Round 1. digit AFTER decimal point // Round 1. digit AFTER decimal point
piecewise.ceiling(12.0654, option.Some(1)) piecewise.ceiling(12.0654, option.Some(1))
|> should.equal(Ok(12.1)) |> should.equal(12.1)
// Round 0. digit BEFORE decimal point // Round 0. digit BEFORE decimal point
piecewise.ceiling(12.0654, option.Some(0)) piecewise.ceiling(12.0654, option.Some(0))
|> should.equal(Ok(13.0)) |> should.equal(13.0)
// Round 1. digit BEFORE decimal point // Round 1. digit BEFORE decimal point
piecewise.ceiling(12.0654, option.Some(-1)) piecewise.ceiling(12.0654, option.Some(-1))
|> should.equal(Ok(20.0)) |> should.equal(20.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.ceiling(12.0654, option.Some(-2)) piecewise.ceiling(12.0654, option.Some(-2))
|> should.equal(Ok(100.0)) |> should.equal(100.0)
// Round 3. digit BEFORE decimal point // Round 3. digit BEFORE decimal point
piecewise.ceiling(12.0654, option.Some(-3)) piecewise.ceiling(12.0654, option.Some(-3))
|> should.equal(Ok(1000.0)) |> should.equal(1000.0)
} }
pub fn float_floor_test() { pub fn float_floor_test() {
// Round 3. digit AFTER decimal point // Round 3. digit AFTER decimal point
piecewise.floor(12.0654, option.Some(3)) piecewise.floor(12.0654, option.Some(3))
|> should.equal(Ok(12.065)) |> should.equal(12.065)
// Round 2. digit AFTER decimal point // Round 2. digit AFTER decimal point
piecewise.floor(12.0654, option.Some(2)) piecewise.floor(12.0654, option.Some(2))
|> should.equal(Ok(12.06)) |> should.equal(12.06)
// Round 1. digit AFTER decimal point // Round 1. digit AFTER decimal point
piecewise.floor(12.0654, option.Some(1)) piecewise.floor(12.0654, option.Some(1))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 0. digit BEFORE decimal point // Round 0. digit BEFORE decimal point
piecewise.floor(12.0654, option.Some(0)) piecewise.floor(12.0654, option.Some(0))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 1. digit BEFORE decimal point // Round 1. digit BEFORE decimal point
piecewise.floor(12.0654, option.Some(-1)) piecewise.floor(12.0654, option.Some(-1))
|> should.equal(Ok(10.0)) |> should.equal(10.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.floor(12.0654, option.Some(-2)) piecewise.floor(12.0654, option.Some(-2))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.floor(12.0654, option.Some(-3)) piecewise.floor(12.0654, option.Some(-3))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
} }
pub fn float_truncate_test() { pub fn float_truncate_test() {
// Round 3. digit AFTER decimal point // Round 3. digit AFTER decimal point
piecewise.truncate(12.0654, option.Some(3)) piecewise.truncate(12.0654, option.Some(3))
|> should.equal(Ok(12.065)) |> should.equal(12.065)
// Round 2. digit AFTER decimal point // Round 2. digit AFTER decimal point
piecewise.truncate(12.0654, option.Some(2)) piecewise.truncate(12.0654, option.Some(2))
|> should.equal(Ok(12.06)) |> should.equal(12.06)
// Round 1. digit AFTER decimal point // Round 1. digit AFTER decimal point
piecewise.truncate(12.0654, option.Some(1)) piecewise.truncate(12.0654, option.Some(1))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 0. digit BEFORE decimal point // Round 0. digit BEFORE decimal point
piecewise.truncate(12.0654, option.Some(0)) piecewise.truncate(12.0654, option.Some(0))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 1. digit BEFORE decimal point // Round 1. digit BEFORE decimal point
piecewise.truncate(12.0654, option.Some(-1)) piecewise.truncate(12.0654, option.Some(-1))
|> should.equal(Ok(10.0)) |> should.equal(10.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.truncate(12.0654, option.Some(-2)) piecewise.truncate(12.0654, option.Some(-2))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.truncate(12.0654, option.Some(-3)) piecewise.truncate(12.0654, option.Some(-3))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
} }
pub fn math_round_to_nearest_test() { pub fn math_round_to_nearest_test() {
// Try with positive values // Try with positive values
piecewise.round(1.5, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(1.5, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(2.0)) |> should.equal(2.0)
piecewise.round(1.75, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(1.75, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(2.0)) |> should.equal(2.0)
piecewise.round(2.0, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(2.0, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(2.0)) |> should.equal(2.0)
piecewise.round(3.5, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(3.5, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(4.0)) |> should.equal(4.0)
piecewise.round(4.5, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(4.5, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(4.0)) |> should.equal(4.0)
// Try with negative values // Try with negative values
piecewise.round(-3.5, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(-3.5, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(-4.0)) |> should.equal(-4.0)
piecewise.round(-4.5, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(-4.5, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(-4.0)) |> should.equal(-4.0)
// Round 3. digit AFTER decimal point // Round 3. digit AFTER decimal point
piecewise.round(12.0654, option.Some(3), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(3), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(12.065)) |> should.equal(12.065)
// Round 2. digit AFTER decimal point // Round 2. digit AFTER decimal point
piecewise.round(12.0654, option.Some(2), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(2), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(12.07)) |> should.equal(12.07)
// Round 1. digit AFTER decimal point // Round 1. digit AFTER decimal point
piecewise.round(12.0654, option.Some(1), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(1), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(12.1)) |> should.equal(12.1)
// Round 0. digit BEFORE decimal point // Round 0. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(0), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(0), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 1. digit BEFORE decimal point // Round 1. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(-1), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(-1), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(10.0)) |> should.equal(10.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(-2), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(-2), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
// Round 3. digit BEFORE decimal point // Round 3. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(-3), option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.Some(-3), option.Some(piecewise.RoundNearest))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
} }
pub fn math_round_up_test() { pub fn math_round_up_test() {
// Note: Rounding mode "RoundUp" is an alias for the ceiling function // Note: Rounding mode "RoundUp" is an alias for the ceiling function
// Try with positive values // Try with positive values
piecewise.round(0.45, option.Some(0), option.Some(piecewise.RoundUp)) piecewise.round(0.45, option.Some(0), option.Some(piecewise.RoundUp))
|> should.equal(Ok(1.0)) |> should.equal(1.0)
piecewise.round(0.5, option.Some(0), option.Some(piecewise.RoundUp)) piecewise.round(0.5, option.Some(0), option.Some(piecewise.RoundUp))
|> should.equal(Ok(1.0)) |> should.equal(1.0)
piecewise.round(0.45, option.Some(1), option.Some(piecewise.RoundUp)) piecewise.round(0.45, option.Some(1), option.Some(piecewise.RoundUp))
|> should.equal(Ok(0.5)) |> should.equal(0.5)
piecewise.round(0.5, option.Some(1), option.Some(piecewise.RoundUp)) piecewise.round(0.5, option.Some(1), option.Some(piecewise.RoundUp))
|> should.equal(Ok(0.5)) |> should.equal(0.5)
piecewise.round(0.455, option.Some(2), option.Some(piecewise.RoundUp)) piecewise.round(0.455, option.Some(2), option.Some(piecewise.RoundUp))
|> should.equal(Ok(0.46)) |> should.equal(0.46)
piecewise.round(0.505, option.Some(2), option.Some(piecewise.RoundUp)) piecewise.round(0.505, option.Some(2), option.Some(piecewise.RoundUp))
|> should.equal(Ok(0.51)) |> should.equal(0.51)
// Try with negative values // Try with negative values
piecewise.round(-0.45, option.Some(0), option.Some(piecewise.RoundUp)) piecewise.round(-0.45, option.Some(0), option.Some(piecewise.RoundUp))
|> should.equal(Ok(-0.0)) |> should.equal(-0.0)
piecewise.round(-0.5, option.Some(0), option.Some(piecewise.RoundUp)) piecewise.round(-0.5, option.Some(0), option.Some(piecewise.RoundUp))
|> should.equal(Ok(-0.0)) |> should.equal(-0.0)
piecewise.round(-0.45, option.Some(1), option.Some(piecewise.RoundUp)) piecewise.round(-0.45, option.Some(1), option.Some(piecewise.RoundUp))
|> should.equal(Ok(-0.4)) |> should.equal(-0.4)
piecewise.round(-0.5, option.Some(1), option.Some(piecewise.RoundUp)) piecewise.round(-0.5, option.Some(1), option.Some(piecewise.RoundUp))
|> should.equal(Ok(-0.5)) |> should.equal(-0.5)
piecewise.round(-0.455, option.Some(2), option.Some(piecewise.RoundUp)) piecewise.round(-0.455, option.Some(2), option.Some(piecewise.RoundUp))
|> should.equal(Ok(-0.45)) |> should.equal(-0.45)
piecewise.round(-0.505, option.Some(2), option.Some(piecewise.RoundUp)) piecewise.round(-0.505, option.Some(2), option.Some(piecewise.RoundUp))
|> should.equal(Ok(-0.5)) |> should.equal(-0.5)
} }
pub fn math_round_down_test() { pub fn math_round_down_test() {
// Note: Rounding mode "RoundDown" is an alias for the floor function // Note: Rounding mode "RoundDown" is an alias for the floor function
// Try with positive values // Try with positive values
piecewise.round(0.45, option.Some(0), option.Some(piecewise.RoundDown)) piecewise.round(0.45, option.Some(0), option.Some(piecewise.RoundDown))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
piecewise.round(0.5, option.Some(0), option.Some(piecewise.RoundDown)) piecewise.round(0.5, option.Some(0), option.Some(piecewise.RoundDown))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
piecewise.round(0.45, option.Some(1), option.Some(piecewise.RoundDown)) piecewise.round(0.45, option.Some(1), option.Some(piecewise.RoundDown))
|> should.equal(Ok(0.4)) |> should.equal(0.4)
piecewise.round(0.5, option.Some(1), option.Some(piecewise.RoundDown)) piecewise.round(0.5, option.Some(1), option.Some(piecewise.RoundDown))
|> should.equal(Ok(0.5)) |> should.equal(0.5)
piecewise.round(0.455, option.Some(2), option.Some(piecewise.RoundDown)) piecewise.round(0.455, option.Some(2), option.Some(piecewise.RoundDown))
|> should.equal(Ok(0.45)) |> should.equal(0.45)
piecewise.round(0.505, option.Some(2), option.Some(piecewise.RoundDown)) piecewise.round(0.505, option.Some(2), option.Some(piecewise.RoundDown))
|> should.equal(Ok(0.5)) |> should.equal(0.5)
// Try with negative values // Try with negative values
piecewise.round(-0.45, option.Some(0), option.Some(piecewise.RoundDown)) piecewise.round(-0.45, option.Some(0), option.Some(piecewise.RoundDown))
|> should.equal(Ok(-1.0)) |> should.equal(-1.0)
piecewise.round(-0.5, option.Some(0), option.Some(piecewise.RoundDown)) piecewise.round(-0.5, option.Some(0), option.Some(piecewise.RoundDown))
|> should.equal(Ok(-1.0)) |> should.equal(-1.0)
piecewise.round(-0.45, option.Some(1), option.Some(piecewise.RoundDown)) piecewise.round(-0.45, option.Some(1), option.Some(piecewise.RoundDown))
|> should.equal(Ok(-0.5)) |> should.equal(-0.5)
piecewise.round(-0.5, option.Some(1), option.Some(piecewise.RoundDown)) piecewise.round(-0.5, option.Some(1), option.Some(piecewise.RoundDown))
|> should.equal(Ok(-0.5)) |> should.equal(-0.5)
piecewise.round(-0.455, option.Some(2), option.Some(piecewise.RoundDown)) piecewise.round(-0.455, option.Some(2), option.Some(piecewise.RoundDown))
|> should.equal(Ok(-0.46)) |> should.equal(-0.46)
piecewise.round(-0.505, option.Some(2), option.Some(piecewise.RoundDown)) piecewise.round(-0.505, option.Some(2), option.Some(piecewise.RoundDown))
|> should.equal(Ok(-0.51)) |> should.equal(-0.51)
} }
pub fn math_round_to_zero_test() { pub fn math_round_to_zero_test() {
// Note: Rounding mode "RoundToZero" is an alias for the truncate function // Note: Rounding mode "RoundToZero" is an alias for the truncate function
// Try with positive values // Try with positive values
piecewise.round(0.5, option.Some(0), option.Some(piecewise.RoundToZero)) piecewise.round(0.5, option.Some(0), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
piecewise.round(0.75, option.Some(0), option.Some(piecewise.RoundToZero)) piecewise.round(0.75, option.Some(0), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
piecewise.round(0.45, option.Some(1), option.Some(piecewise.RoundToZero)) piecewise.round(0.45, option.Some(1), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.4)) |> should.equal(0.4)
piecewise.round(0.57, option.Some(1), option.Some(piecewise.RoundToZero)) piecewise.round(0.57, option.Some(1), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.5)) |> should.equal(0.5)
piecewise.round(0.4575, option.Some(2), option.Some(piecewise.RoundToZero)) piecewise.round(0.4575, option.Some(2), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.45)) |> should.equal(0.45)
piecewise.round(0.5075, option.Some(2), option.Some(piecewise.RoundToZero)) piecewise.round(0.5075, option.Some(2), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.5)) |> should.equal(0.5)
// Try with negative values // Try with negative values
piecewise.round(-0.5, option.Some(0), option.Some(piecewise.RoundToZero)) piecewise.round(-0.5, option.Some(0), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
piecewise.round(-0.75, option.Some(0), option.Some(piecewise.RoundToZero)) piecewise.round(-0.75, option.Some(0), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
piecewise.round(-0.45, option.Some(1), option.Some(piecewise.RoundToZero)) piecewise.round(-0.45, option.Some(1), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(-0.4)) |> should.equal(-0.4)
piecewise.round(-0.57, option.Some(1), option.Some(piecewise.RoundToZero)) piecewise.round(-0.57, option.Some(1), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(-0.5)) |> should.equal(-0.5)
piecewise.round(-0.4575, option.Some(2), option.Some(piecewise.RoundToZero)) piecewise.round(-0.4575, option.Some(2), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(-0.45)) |> should.equal(-0.45)
piecewise.round(-0.5075, option.Some(2), option.Some(piecewise.RoundToZero)) piecewise.round(-0.5075, option.Some(2), option.Some(piecewise.RoundToZero))
|> should.equal(Ok(-0.5)) |> should.equal(-0.5)
} }
pub fn math_round_ties_away_test() { pub fn math_round_ties_away_test() {
// Try with positive values // Try with positive values
piecewise.round(1.4, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(1.4, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(1.0)) |> should.equal(1.0)
piecewise.round(1.5, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(1.5, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(2.0)) |> should.equal(2.0)
piecewise.round(2.5, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(2.5, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(3.0)) |> should.equal(3.0)
// Try with negative values // Try with negative values
piecewise.round(-1.4, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(-1.4, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(-1.0)) |> should.equal(-1.0)
piecewise.round(-1.5, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(-1.5, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(-2.0)) |> should.equal(-2.0)
piecewise.round(-2.0, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(-2.0, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(-2.0)) |> should.equal(-2.0)
piecewise.round(-2.5, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(-2.5, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(-3.0)) |> should.equal(-3.0)
// Round 3. digit AFTER decimal point // Round 3. digit AFTER decimal point
piecewise.round(12.0654, option.Some(3), option.Some(piecewise.RoundTiesAway)) piecewise.round(12.0654, option.Some(3), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(12.065)) |> should.equal(12.065)
// Round 2. digit AFTER decimal point // Round 2. digit AFTER decimal point
piecewise.round(12.0654, option.Some(2), option.Some(piecewise.RoundTiesAway)) piecewise.round(12.0654, option.Some(2), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(12.07)) |> should.equal(12.07)
// Round 1. digit AFTER decimal point // Round 1. digit AFTER decimal point
piecewise.round(12.0654, option.Some(1), option.Some(piecewise.RoundTiesAway)) piecewise.round(12.0654, option.Some(1), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(12.1)) |> should.equal(12.1)
// Round 0. digit BEFORE decimal point // Round 0. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(0), option.Some(piecewise.RoundTiesAway)) piecewise.round(12.0654, option.Some(0), option.Some(piecewise.RoundTiesAway))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 1. digit BEFORE decimal point // Round 1. digit BEFORE decimal point
piecewise.round( piecewise.round(
@ -316,7 +316,7 @@ pub fn math_round_ties_away_test() {
option.Some(-1), option.Some(-1),
option.Some(piecewise.RoundTiesAway), option.Some(piecewise.RoundTiesAway),
) )
|> should.equal(Ok(10.0)) |> should.equal(10.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.round( piecewise.round(
@ -324,7 +324,7 @@ pub fn math_round_ties_away_test() {
option.Some(-2), option.Some(-2),
option.Some(piecewise.RoundTiesAway), option.Some(piecewise.RoundTiesAway),
) )
|> should.equal(Ok(0.0)) |> should.equal(0.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.round( piecewise.round(
@ -332,70 +332,70 @@ pub fn math_round_ties_away_test() {
option.Some(-3), option.Some(-3),
option.Some(piecewise.RoundTiesAway), option.Some(piecewise.RoundTiesAway),
) )
|> should.equal(Ok(0.0)) |> should.equal(0.0)
} }
pub fn math_round_ties_up_test() { pub fn math_round_ties_up_test() {
// Try with positive values // Try with positive values
piecewise.round(1.4, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(1.4, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(1.0)) |> should.equal(1.0)
piecewise.round(1.5, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(1.5, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(2.0)) |> should.equal(2.0)
piecewise.round(2.5, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(2.5, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(3.0)) |> should.equal(3.0)
// Try with negative values // Try with negative values
piecewise.round(-1.4, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(-1.4, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(-1.0)) |> should.equal(-1.0)
piecewise.round(-1.5, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(-1.5, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(-1.0)) |> should.equal(-1.0)
piecewise.round(-2.0, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(-2.0, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(-2.0)) |> should.equal(-2.0)
piecewise.round(-2.5, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(-2.5, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(-2.0)) |> should.equal(-2.0)
// Round 3. digit AFTER decimal point // Round 3. digit AFTER decimal point
piecewise.round(12.0654, option.Some(3), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(3), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(12.065)) |> should.equal(12.065)
// Round 2. digit AFTER decimal point // Round 2. digit AFTER decimal point
piecewise.round(12.0654, option.Some(2), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(2), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(12.07)) |> should.equal(12.07)
// Round 1. digit AFTER decimal point // Round 1. digit AFTER decimal point
piecewise.round(12.0654, option.Some(1), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(1), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(12.1)) |> should.equal(12.1)
// Round 0. digit BEFORE decimal point // Round 0. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(0), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(0), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// Round 1. digit BEFORE decimal point // Round 1. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(-1), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(-1), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(10.0)) |> should.equal(10.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(-2), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(-2), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
// Round 2. digit BEFORE decimal point // Round 2. digit BEFORE decimal point
piecewise.round(12.0654, option.Some(-3), option.Some(piecewise.RoundTiesUp)) piecewise.round(12.0654, option.Some(-3), option.Some(piecewise.RoundTiesUp))
|> should.equal(Ok(0.0)) |> should.equal(0.0)
} }
pub fn math_round_edge_cases_test() { pub fn math_round_edge_cases_test() {
// The default number of digits is 0 if None is provided // The default number of digits is 0 if None is provided
piecewise.round(12.0654, option.None, option.Some(piecewise.RoundNearest)) piecewise.round(12.0654, option.None, option.Some(piecewise.RoundNearest))
|> should.equal(Ok(12.0)) |> should.equal(12.0)
// The default rounding mode is piecewise.RoundNearest if None is provided // The default rounding mode is piecewise.RoundNearest if None is provided
piecewise.round(12.0654, option.None, option.None) piecewise.round(12.0654, option.None, option.None)
|> should.equal(Ok(12.0)) |> should.equal(12.0)
} }
pub fn float_absolute_value_test() { pub fn float_absolute_value_test() {