Created
November 7, 2018 17:12
-
-
Save leifwickland/c3bcdb6cd2fa533a5780140e07d03fa6 to your computer and use it in GitHub Desktop.
Refined percentage
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/// A double floating point number which allows values in the range [0.0,100.0]. | |
object ProperPercentage { | |
type L = W.`0.0`.T | |
type H = W.`100.0`.T | |
type P = Interval.Closed[L, H] | |
type N = Double | |
type T = N Refined P | |
val gen: Gen[Refined[N, Closed[L, H]]] = intervalClosedArbitrary[Refined, N, L, H].arbitrary | |
def safely(d: Double): String \/ T = refineV[P].apply(d).fold(_.left, _.right) | |
def unsafe(d: Double): T = safely(d).valueOr(m => throw new Exception(m)) | |
val Zero: T = unsafe(0.0) | |
val OneHundred: T = unsafe(100.0) | |
def asFraction(p: T): Double = p.value / 100.0 | |
def fromFraction(d: Double): String \/ T = safely(d * 100D) | |
} | |
/** | |
* Add `refine` and `unsafe` to the companion object of a class which is a simple wrapper around `ProperPercentage.T`. | |
*/ | |
trait ProperPercentageWrapper { | |
type W | |
val wrap: ProperPercentage.T => W | |
def safely(d: Double): String \/ W = ProperPercentage.safely(d).map(wrap) | |
def unsafe(d: Double): W = safely(d).valueOr(m => throw new Exception(m)) | |
def unwrap(w: W): ProperPercentage.T | |
implicit val orderingW: Ordering[W] = Ordering.by(w => unwrap(w).value) | |
implicit val orderW: Order[W] = Order.fromScalaOrdering(orderingW) | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
case class SampleRate(r: ProperPercentage.T) | |
object SampleRate extends ProperPercentageWrapper { | |
type W = SampleRate | |
val wrap: T => SampleRate = SampleRate.apply | |
def unwrap(w: SampleRate): T = w.r | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment