SuperCollider has had the great feature of implementing List Comprehension for decades.
But taking a look around the source code, I found a strange syntax that I don’t remember being documented anywhere. And it’s not an “exotic” curiosity, it’s a sophisticated feature.
Have you ever seen List Comprehensions using {; instead of {:? These aren’t your typical list comprehensions, but they’ve got some similar vibes. I will call it “Monad Comprehension”, because that’s a way it could be interpreted in Haskell.
This one gives you control over what gets yielded and when.
{; x*2, x <- (2..6)} // Immediately outputs the first result: 2
Use {; when you only want to output specific results or need to control outputs based on certain conditions, present of past states, etc.
It doesn’t exist as List Comprehension in Haskell, but can be achieved as a Monad Comprehension. See:
import Control.Monad (guard)
doubleIfGreaterThanFive :: Int -> Maybe Int
doubleIfGreaterThanFive x = do
guard (x > 5) -- If x is not greater than 5, the computation outputs Nothing
return (x * 2) -- Otherwise, return Just the doubled value
processList :: [Int] -> [Maybe Int]
processList xs = do
x <- xs
return (doubleIfGreaterThanFive x)
main :: IO ()
main = print $ processList [3, 6, 8, 2, 10, 1]