idiom brackets
In our paper, Ross and I used Scott-brackets for idiomatic lifting. For a while, I had a cheeky typeclass hack, but it seemed like overkill, especially as it didn't nest. She now supports a notation which does the job.
In our paper, Ross and I used Scott-brackets for idiomatic lifting. For a while, I had a cheeky typeclass hack, but it seemed like overkill, especially as it didn't nest. She now supports a notation which does the job.
Write
(|f a1 .. an|)
pure f <*> a1 <*> .. <*> an
Infix bonus: (| blah blah +-*/ rhubarb custard |) does the same thing as (|(+-*/) (blah blah) (rhubarb custard)|).
Now you get
instance Traversable [] where
traverse f [] = (|[]|)
traverse f (x : xs) = (|f x : traverse f xs|)
If your Applicative is Alternative, there's a wee extension of this notation that might help. (|) denotes failure (what's ‘empty’ in Control.Applicative). Meanwhile, if you have more than one choice, you can write (| blah1 | .. | blahn |) where each blah is an application in the form described above. I've been careful to make sure that you only need an Alternative instance if you provide a number of options other than one.
I like
(| blah1
| ..
| blahn
|)
We've got three combinators in the library, (<$), (<*), and (*>), which let you do things and ignore their values. To achieve the same effect, put this ‘noise’ in (%..%) brackets. For example, we can write a wee parser like this:
pExp :: P Char Exp
pExp =
(| Neg (%teq '-'%) pExp
| (:+:) (%teq '('%) pExp (%teq '+'%) pExp (%teq ')'%)
| V (tok isAlpha)
|)
If you want to mix impure and pure arguments, you can stick ~ in front of the pure ones. For example, (|lookup token ~ keywordList|).
In monadic idioms, we sometimes compute computations. Postfixing @ computes the value of a computed computation: it just applies join to the story so far. Safe conditional expression is (|cond notADrill ~ launchMissiles ~ (|()|)) @ |).