Skip to content

Instantly share code, notes, and snippets.

@bvenners
Last active August 29, 2015 14:08
Show Gist options
  • Save bvenners/844e9a83687d0cd3c80f to your computer and use it in GitHub Desktop.
Save bvenners/844e9a83687d0cd3c80f to your computer and use it in GitHub Desktop.
Currently brewing in Scalactic master: bounded AnyVal types, including Pos (a positive Int)
scala> import org.scalactic.numbers._
import numbers._
// Pos is a type that ensures its "contained" value is a positive Int. I put "contained"
// in scare quotes because Pos is an AnyVal, so it should only box when an Int would box.
// You can create them directly with positive integer literals, like this:
scala> Pos(3)
res0: org.scalactic.numbers.Pos = Pos(3)
// If you pass an Int variable, or a non-positive Int literal, to this factory method, it
// won't compile:
scala> Pos(-3)
<console>:20: error: Pos.apply can only be invoked on a positive (i > 0) integer literal, like Pos(42). Please
use Pos.from instead.
Pos(-3)
^
scala> val x = 3
x: Int = 3
scala> Pos(x)
<console>:21: error: Pos.apply can only be invoked on a positive (i > 0) integer literal, like Pos(42). Please
use Pos.from instead.
Pos(x)
^
// The Pos.from factory will work on any value of type Int, but gives back an Option[Pos]
scala> Pos.from(3)
res3: Option[org.scalactic.numbers.Pos] = Some(Pos(3))
scala> Pos.from(-3)
res4: Option[org.scalactic.numbers.Pos] = None
scala> Pos.from(x)
res5: Option[org.scalactic.numbers.Pos] = Some(Pos(3))
// You can use a Pos where an Int is required
scala> def takesInt(i: Int): Int = i + 1
takesInt: (i: Int)Int
scala> takesInt(Pos(3))
res6: Int = 4
// You can also use a valid Int literal where a Pos is required.
scala> def takesPos(pos: Pos): Int = pos + 1
takesPos: (pos: org.scalactic.numbers.Pos)Int
scala> takesPos(Pos(3))
res7: Int = 4
scala> takesPos(3)
res8: Int = 4
// As with the Pos apply factory, you'll get a compiler error if you try to use
// an Int variable or non-positive Int literal where an Int is required.
scala> takesPos(-3)
<console>:21: error: Pos.apply can only be invoked on a positive (i > 0) integer literal, like Pos(42). Please
use Pos.from instead.
takesPos(-3)
^
scala> takesPos(x)
<console>:22: error: Pos.apply can only be invoked on a positive (i > 0) integer literal, like Pos(42). Please
use Pos.from instead.
takesPos(x)
^
// You'll be able to use Pos with any operator you can use on Int, but if there's any chance
// you could end up with a negative number, you'll get an Int as the result:
scala> Pos(3) + Pos(4)
res11: Int = 7
// Here's an example where the + operator yields a negative Int:
scala> Pos(3) + Pos(Int.MaxValue)
res12: Int = -2147483646
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment