diff --git a/Data/Patch.hs b/Data/Patch.hs
--- a/Data/Patch.hs
+++ b/Data/Patch.hs
@@ -21,6 +21,10 @@
        , index
        , old
        , new
+         -- * Viewing Patches and Hunks
+       , Hunks
+       , HunkStatus (..)
+       , hunks
        )
        where
 
diff --git a/Data/Patch/Internal.hs b/Data/Patch/Internal.hs
--- a/Data/Patch/Internal.hs
+++ b/Data/Patch/Internal.hs
@@ -231,6 +231,9 @@
 --
 --   prop> forAll (divergingPatchesFrom d) $ \(p,q) -> let (p', q') = transformWith (*) p q; (q'', p'') = transformWith (*) q p in p' == p'' && q' == q''
 --
+--   prop> forAll (patchesFrom d) $ \ p -> transformWith (*) mempty p == (mempty, p)
+--   prop> forAll (patchesFrom d) $ \ p -> transformWith (*) p mempty == (p, mempty)
+--
 --   Some example conflict strategies are provided below.
 transformWith :: (Eq a) => (a -> a -> a) -> Patch a -> Patch a -> (Patch a, Patch a)
 transformWith conflict (Patch p) (Patch q)
@@ -256,8 +259,10 @@
                           (go xs a ys b)
            (Insert {}, _) -> over _1 (over index (+ a) x:) $ go xs a (y:ys) (b + offset x)
            (_, Insert {}) -> over _2 (over index (+ b) y:) $ go (x:xs) (a + offset y) ys b
-           (Replace {}, Delete  {}) -> over _2 (over index (+ b) y:) $ go xs (a + offset y) ys b
-           (Delete  {}, Replace {}) -> over _1 (over index (+ a) x:) $ go xs a ys (b + offset x)
+           (Replace i _ nx, Delete  {})
+             -> over _2 (over index (+ b) (Delete i nx):) $ go xs (a + offset y) ys b
+           (Delete  {}, Replace i _ ny)
+             -> over _1 (over index (+ a) (Delete i ny):) $ go xs a ys (b + offset x)
            (Delete  {}, Delete  {}) -> go xs (a + offset y) ys (b + offset x)
     offset (Insert {})  =  1
     offset (Delete {})  = -1
@@ -303,3 +308,30 @@
                                                _         -> 1
                     }
 
+
+
+-- | The four different ways a hunk may have been manipulated.
+data HunkStatus = Inserted | Deleted | Replaced | Unchanged deriving (Eq, Show, Read)
+
+-- | The type for a series of hunks; a patch as it may be displayed to a user.
+type Hunks a = [(Vector a, HunkStatus)]
+
+-- | Render a patch on a document as a list of change hunks. Good for displaying
+--   a patch to a user.
+--
+--   prop> forAll (patchesFrom d) $ \p -> Vector.concat (map fst (filter ((/= Deleted) . snd) (hunks p d))) == apply p d
+hunks :: Patch a -> Vector a -> Hunks a
+hunks (Patch s) i = map eachGroup $ List.groupBy ((==) `on` snd) $ go s i 0
+  where go [] v _ | Vector.null v = []
+                  | otherwise     = [(v, Unchanged)]
+        go (a : as) v x
+          | x' <- a ^. index
+          = let (prefix, rest) = Vector.splitAt (x' - x) v
+                hunk (Insert _ c) = (Vector.singleton c, Inserted)
+                hunk (Replace _ _ c) = (Vector.singleton c, Replaced)
+                hunk (Delete _ c) = (Vector.singleton c, Deleted)
+                offset (Insert {}) = 0
+                offset _ = 1
+             in (if x' > x then ((prefix,Unchanged) :) else id) $ hunk a : go as (Vector.drop (offset a) rest) (x' + offset a)
+        eachGroup r@((_,st):_) = (Vector.concat (map fst r), st)
+        eachGroup [] = error "impossible!"
diff --git a/patches-vector.cabal b/patches-vector.cabal
--- a/patches-vector.cabal
+++ b/patches-vector.cabal
@@ -2,7 +2,7 @@
 -- documentation, see http://haskell.org/cabal/users-guide/
 
 name:                patches-vector
-version:             0.1.1.0
+version:             0.1.2.0
 synopsis:            Patches (diffs) on vectors: composable, mergeable, and invertible.
 description:         A patch is a collection of modifications (edits) to be made to a sequence of elements. Commonly
                      found in version control systems, patches are also a simple example of a group, supporting composition
