Skip to content

Instantly share code, notes, and snippets.

@zah
Created November 24, 2011 19:23
Show Gist options
  • Select an option

  • Save zah/1392058 to your computer and use it in GitHub Desktop.

Select an option

Save zah/1392058 to your computer and use it in GitHub Desktop.
The case for Option[T]
# Option[T] and safe navigation:
# Some languages have a specialized syntax for what is usually called "safe navigation"
foo?.bar[10]?.baz
# Option[T] could be implemented as a proxy type that rewrites any operation on it
# as a operation applied to the stored value (if there is any)
# The original example then becomes:
Option(foo).bar[10].baz # returns Option[type(baz)]
# Another point to note: proxy types used in this fashion are pretty much equivalent to Haskell's monads
# Option[T] and the HLO:
# One can write a rule similar to this:
template { if(x): body } (x: Option[T]) =
if(x.hasValue):
var x = x.value
block: body
# Thus achieving both achiving both convenient syntax and perfect generated code
# Other similar clever tricks are possible with "symbol attached user properties" to implement the type state logic
# And finally, Option[T] is a meta-type (type describing additional properties of another type)
# using meta types is good because they encode the intention of the library writter and allow
# algorithms similar to the above to be executed over the program as a whole.
@zah
Copy link
Author

zah commented Nov 25, 2011

The pattern here is intentionally simplified. In reality, it has to check that the matched symbol is a local variable of type Option[T]. Since, inside the if, it has been proven that the option[T] has value, the goal of the transformation is to hide the Option[T] variable and replace it with the actual value in the inner scope (the body of the if). Thus you don't pay for any further "is valid" checks inside the if.

Certainly, there exists cases for which Option[T] is overkill and sensible return value can be used instead (this spares the need for if on the result for users), but there are many problem domains in which sensible default just doesn't exist.

Also, there are many data structures for which the pattern:

if exists(key):
   var value = get(key)

will perform two expensive searches rather than just one as it is in:

var found = find(key)
if found:
   use found

Finally, the safe navigation feature is handled rather nicely with option[T] and there is no good alternative for that. (even if special syntax like foo?.bar.baz? is introduced, it still have to match agains some specific types - Option[T] is a good alternative to nullable pointer types, because its behaves better with stack value semantics)

Someone will implement the Option[T] type anyway, my suggestion is that it's better if the most popular implementation is in the standard library

@Araq
Copy link

Araq commented Nov 27, 2011

Ok, fair enough. ;-)

However, the HLO can also easily deal with

if exists(key):
  var value = get(key)

@zah
Copy link
Author

zah commented Nov 28, 2011

For completeness, here is the other approach of optimizing Option[T] using "attached symbol properties" (cookies):
The if statement involving Option[T] is transformed to:

if x.hasValue:
   addScopedSymProp(x, "ProvenToHaveValue", true)
   body

then the proxy macro code in Option[T] detects the ProvenToHaveValue "cookie" and generates code without checks

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment