diff --git a/Data/Stream.hs b/Data/Stream.hs
--- a/Data/Stream.hs
+++ b/Data/Stream.hs
@@ -81,7 +81,7 @@
 infixr 5 `Cons`
 
 instance Functor Stream where
-  fmap f (Cons x xs) = Cons (f x) (fmap f xs)
+  fmap f ~(Cons x xs) = Cons (f x) (fmap f xs)
 
 instance Applicative Stream where
   pure = repeat
@@ -92,7 +92,7 @@
   xs >>= f = join (fmap f xs)
     where
       join :: Stream (Stream a) -> Stream a
-      join (Cons xs xss) = Cons (head xs) (join (map tail xss))
+      join ~(Cons xs xss) = Cons (head xs) (join (map tail xss))
 
 instance Arbitrary a => Arbitrary (Stream a) where
   arbitrary = liftM2 Cons arbitrary arbitrary
@@ -129,7 +129,7 @@
 
 -- | Extract the sequence following the head of the stream.
 tail :: Stream a -> Stream a
-tail (Cons _ xs) = xs
+tail ~(Cons _ xs) = xs
 
 -- | The 'inits' function takes a stream @xs@ and returns all the
 -- finite prefixes of @xs@.
@@ -152,25 +152,25 @@
 
 -- | Apply a function uniformly over all elements of a sequence.
 map :: (a -> b) -> Stream a -> Stream b
-map f (Cons x xs) = Cons (f x) (map f xs)
+map f ~(Cons x xs) = Cons (f x) (map f xs)
 
 -- | 'intersperse' @y@ @xs@ creates an alternating stream of
 -- elements from @xs@ and @y@.
 intersperse :: a -> Stream a -> Stream a
-intersperse y (Cons x xs) = Cons x (Cons y (intersperse y xs))
+intersperse y ~(Cons x xs) = Cons x (Cons y (intersperse y xs))
 
 -- | Interleave two Streams @xs@ and @ys@, alternating elements
 -- from each list.
 --
 -- > [x1,x2,...] `interleave` [y1,y2,...] == [x1,y1,x2,y2,...]
 interleave :: Stream a -> Stream a -> Stream a
-interleave (Cons x xs) ys = Cons x (interleave ys xs)
+interleave ~(Cons x xs) ys = Cons x (interleave ys xs)
 
 -- | 'scan' yields a stream of successive reduced values from:
 --
 -- > scan f z [x1, x2, ...] == [z, z `f` x1, (z `f` x1) `f` x2, ...]
 scan :: (a -> b -> a) -> a -> Stream b -> Stream a
-scan f z (Cons x xs) =  z <:> scan f (f z x) xs
+scan f z ~(Cons x xs) =  z <:> scan f (f z x) xs
 
 -- | @scan'@ is a strict scan.
 scan' :: (a -> b -> a) -> a -> Stream b -> Stream a
@@ -180,15 +180,15 @@
 --
 -- > scan1 f [x1, x2, ...] == [x1, x1 `f` x2, ...]
 scan1 :: (a -> a -> a) -> Stream a -> Stream a
-scan1 f (Cons x xs) = scan f x xs
+scan1 f ~(Cons x xs) = scan f x xs
 
 -- | @scan1'@ is a strict scan that has no starting value.
 scan1' :: (a -> a -> a) -> Stream a -> Stream a
-scan1' f (Cons x xs) = scan' f x xs
+scan1' f ~(Cons x xs) = scan' f x xs
 
 -- | 'transpose' computes the transposition of a stream of streams.
 transpose :: Stream (Stream a) -> Stream (Stream a)
-transpose (Cons (Cons x xs) yss) =
+transpose ~(Cons (Cons x xs) yss) =
     (x <:> map head yss) <:> transpose (xs <:> map tail yss)
 
 -- | 'iterate' @f@ @x@ function produces the infinite sequence
@@ -263,7 +263,7 @@
 -- /Beware/: this function may diverge if every element of @xs@
 -- satisfies @p@, e.g.  @dropWhile even (repeat 0)@ will loop.
 dropWhile :: (a -> Bool) -> Stream a -> Stream a
-dropWhile p (Cons x xs)
+dropWhile p ~(Cons x xs)
   | p x       = dropWhile p xs
   | otherwise = Cons x xs
 
@@ -284,7 +284,7 @@
 -- /Beware/: this function may diverge if there is no element of
 -- @xs@ that satisfies @p@, e.g.  @filter odd (repeat 0)@ will loop.
 filter :: (a -> Bool) -> Stream a -> Stream a
-filter p (Cons x xs)
+filter p ~(Cons x xs)
   | p x       = Cons x (filter p xs)
   | otherwise = filter p xs
 
@@ -297,7 +297,7 @@
 -- example, @fst (partition even (repeat 0)) == repeat 0@; on the
 -- other hand @snd (partition even (repeat 0))@ is undefined.
 partition :: (a -> Bool) -> Stream a -> (Stream a, Stream a)
-partition p (Cons x xs) =
+partition p ~(Cons x xs) =
   let (trues,falses) = partition p xs
   in if p x then (Cons x trues, falses)
             else (trues, Cons x falses)
@@ -309,7 +309,7 @@
 --
 -- > group $ cycle "Mississippi" = "M" ::: "i" ::: "ss" ::: "i" ::: "ss" ::: "i" ::: "pp" ::: "i" ::: "M" ::: "i" ::: ...
 group :: Eq a => Stream a -> Stream [a]
-group (Cons x ys) = let (xs, zs) = span (\y -> x == y) ys
+group ~(Cons x ys) = let (xs, zs) = span (\y -> x == y) ys
                     in (x : xs) <:> group zs
 
 -- | The 'isPrefix' function returns @True@ if the first argument is
@@ -376,17 +376,17 @@
 -- | The 'zip' function takes two streams and returns a list of
 -- corresponding pairs.
 zip :: Stream a -> Stream b -> Stream (a,b)
-zip (Cons x xs) (Cons y ys) = Cons (x,y) (zip xs ys)
+zip ~(Cons x xs) ~(Cons y ys) = Cons (x,y) (zip xs ys)
 
 -- | The 'zipWith' function generalizes 'zip'. Rather than tupling
 -- the functions, the elements are combined using the function
 -- passed as the first argument to 'zipWith'.
 zipWith :: (a -> b -> c) -> Stream a -> Stream b -> Stream c
-zipWith f (Cons x xs) (Cons y ys) = Cons (f x y) (zipWith f xs ys)
+zipWith f ~(Cons x xs) ~(Cons y ys) = Cons (f x y) (zipWith f xs ys)
 
 -- | The 'unzip' function is the inverse of the 'zip' function.
 unzip :: Stream (a,b) -> (Stream a, Stream b)
-unzip (Cons (x,y) xys) = (Cons x (fst (unzip xys)),
+unzip ~(Cons (x,y) xys) = (Cons x (fst (unzip xys)),
                                 Cons y (snd (unzip xys)))
 
 -- | The 'words' function breaks a stream of characters into a
@@ -401,7 +401,7 @@
 -- | The 'unwords' function is an inverse operation to 'words'. It
 -- joins words with separating spaces.
 unwords :: Stream String -> Stream Char
-unwords (Cons x xs) = foldr Cons (Cons ' ' (unwords xs)) x
+unwords ~(Cons x xs) = foldr Cons (Cons ' ' (unwords xs)) x
 
 -- | The 'lines' function breaks a stream of characters into a list
 -- of strings at newline characters. The resulting strings do not
@@ -416,7 +416,7 @@
 -- | The 'unlines' function is an inverse operation to 'lines'. It
 -- joins lines, after appending a terminating newline to each.
 unlines :: Stream String -> Stream Char
-unlines (Cons x xs) = foldr Cons (Cons '\n' (unlines xs)) x
+unlines ~(Cons x xs) = foldr Cons (Cons '\n' (unlines xs)) x
 
 -- | The 'toList' converts a stream into an infinite list.
 toList :: Stream a -> [a]
diff --git a/Stream.cabal b/Stream.cabal
--- a/Stream.cabal
+++ b/Stream.cabal
@@ -1,5 +1,5 @@
 Name:                   Stream
-Version:                0.3.2
+Version:                0.4
 License:                BSD3
 License-file:           LICENSE
 Author:                 Wouter Swierstra <wss@cs.nott.ac.uk>,
