diff --git a/ListLike.cabal b/ListLike.cabal
--- a/ListLike.cabal
+++ b/ListLike.cabal
@@ -1,5 +1,5 @@
 Name: ListLike
-Version: 4.5.1
+Version: 4.6
 License: BSD3
 Maintainer: John Lato <jwlato@gmail.com>
 Author: John Goerzen
@@ -60,6 +60,9 @@
                 ,utf8-string
                 ,deepseq
 
+  If !impl(ghc >= 8.4)
+    Build-Depends: semigroups >= 0.16 && < 0.19
+
 Test-suite listlike-tests
   GHC-Options: -O2
   Hs-source-dirs: testsrc
@@ -80,6 +83,8 @@
                   ,text
                   ,vector
                   ,utf8-string
+  If !impl(ghc >= 8.4)
+    Build-Depends: semigroups >= 0.16 && < 0.19
 
 source-repository head
   type:     git
diff --git a/src/Data/ListLike/CharString.hs b/src/Data/ListLike/CharString.hs
--- a/src/Data/ListLike/CharString.hs
+++ b/src/Data/ListLike/CharString.hs
@@ -49,6 +49,7 @@
 import           Data.ListLike.FoldableLL
 import           Data.Int
 import           Data.Monoid
+import           Data.Semigroup (Semigroup(..))
 import qualified Data.ByteString.Char8 as BS
 import qualified Data.ByteString.Lazy.Char8 as BSL
 import qualified System.IO as IO
@@ -63,6 +64,9 @@
 newtype CharString = CS { unCS :: BS.ByteString }
   deriving (Read, Show, Eq, Ord)
 
+instance Semigroup CharString where
+  (<>) = mappend
+
 instance Monoid CharString where
   mempty = CS mempty
   mappend l r = CS $ mappend (unCS l) (unCS r)
@@ -177,6 +181,9 @@
 --   this allows for ListLike instances with Char elements.
 newtype CharStringLazy = CSL { unCSL :: BSL.ByteString }
   deriving (Read, Show, Eq, Ord)
+
+instance Semigroup CharStringLazy where
+  (<>) = mappend
 
 instance Monoid CharStringLazy where
   mempty = CSL mempty
diff --git a/src/Data/ListLike/Chars.hs b/src/Data/ListLike/Chars.hs
--- a/src/Data/ListLike/Chars.hs
+++ b/src/Data/ListLike/Chars.hs
@@ -14,6 +14,7 @@
 import           Control.DeepSeq
 import           Control.Monad
 import           Data.String as String (IsString(fromString))
+import           Data.Semigroup (Semigroup(..))
 import qualified Data.Text.Lazy as T
 import qualified Data.Text.Lazy.IO as TI
 import qualified Data.Text.Lazy.Builder as Builder
@@ -33,6 +34,9 @@
 builder (B x) = x
 builder (T s) = Builder.fromLazyText s
 {-# INLINE builder #-}
+
+instance Semigroup Chars where
+  (<>) = mappend
 
 instance Monoid Chars where
     mempty = B mempty
diff --git a/src/Data/ListLike/Instances.hs b/src/Data/ListLike/Instances.hs
--- a/src/Data/ListLike/Instances.hs
+++ b/src/Data/ListLike/Instances.hs
@@ -52,6 +52,7 @@
 import           Data.Int
 import           Data.Maybe (fromMaybe)
 import           Data.Monoid
+import           Data.Semigroup (Semigroup(..))
 import qualified Data.ByteString as BS
 import qualified Data.ByteString.Char8 as BSC
 import qualified Data.Foldable as F
@@ -338,6 +339,9 @@
     foldr = F.foldr
     foldr1 = F.foldr1
     foldr' = F.foldr'
+
+instance (Integral i, Ix i) => Semigroup (A.Array i e) where
+  (<>) = mappend
 
 instance (Integral i, Ix i) => Monoid (A.Array i e) where
     mempty = A.listArray (0, -1) []
diff --git a/src/Data/ListLike/UTF8.hs b/src/Data/ListLike/UTF8.hs
--- a/src/Data/ListLike/UTF8.hs
+++ b/src/Data/ListLike/UTF8.hs
@@ -29,6 +29,7 @@
 import Data.ListLike.String (StringLike(..))
 import Data.Maybe (fromMaybe)
 import Data.Monoid (Monoid(..))
+import Data.Semigroup (Semigroup(..))
 import Data.String (IsString(fromString))
 import Data.String.UTF8 (UTF8, UTF8Bytes)
 import qualified Data.String.UTF8 as UTF8
@@ -144,6 +145,9 @@
     toString = UTF8.toString
     fromString = UTF8.fromString
 
+instance Semigroup (UTF8 BS.ByteString) where
+  (<>) = mappend
+
 instance Monoid (UTF8 BS.ByteString) where
     mempty = UTF8.fromString []
     mappend a b = UTF8.fromRep (mappend (UTF8.toRep a) (UTF8.toRep b))
@@ -250,6 +254,9 @@
     -- readFile = BSL.readFile
     -- writeFile = BSL.writeFile
     -- appendFile = BSL.appendFile
+
+instance Semigroup (UTF8 BSL.ByteString) where
+  (<>) = mappend
 
 instance StringLike (UTF8 BSL.ByteString) where
     toString = UTF8.toString
diff --git a/src/Data/ListLike/Utils.hs b/src/Data/ListLike/Utils.hs
--- a/src/Data/ListLike/Utils.hs
+++ b/src/Data/ListLike/Utils.hs
@@ -26,7 +26,8 @@
 -}
 
 module Data.ListLike.Utils
-    (and, or, sum, product, zip, zipWith, unzip, sequence_, toMonadPlus, list
+    (and, or, sum, product, zip, zipWith, unzip, sequence_, toMonadPlus, list,
+     intercalate
     ) where
 import Prelude hiding (length, head, last, null, tail, map, filter, concat, 
                        any, lookup, init, all, foldl, foldr, foldl1, foldr1,
@@ -74,3 +75,10 @@
 -- | List-like destructor (like Data.Maybe.maybe)
 list :: ListLike full a => b -> (a -> full -> b) -> full -> b
 list d f = maybe d (uncurry f) . toMonadPlus
+
+-- | 'intercalate' @xs xss@ is equivalent to @('concat' ('intersperse'
+-- xs xss))@.  It inserts the list @xs@ in between the lists in @xss@
+-- and concatenates the result.
+intercalate :: (ListLike a item, ListLike b a)
+            => a -> b -> a
+intercalate x = concat . intersperse x
diff --git a/testsrc/TestInfrastructure.hs b/testsrc/TestInfrastructure.hs
--- a/testsrc/TestInfrastructure.hs
+++ b/testsrc/TestInfrastructure.hs
@@ -29,6 +29,7 @@
 import qualified Data.Array as A
 import qualified Data.DList as DL
 import qualified Data.FMList as FM
+import qualified Data.Semigroup as Sem
 import qualified Data.Sequence as S
 import qualified Data.Foldable as F
 import qualified Data.Text as T
@@ -265,6 +266,8 @@
     foldr1 f (MyList x) = foldr1 f x
     foldl1 f (MyList x) = foldl1 f x
 
+instance Sem.Semigroup (MyList a) where
+  (<>) = mappend
 instance Monoid (MyList a) where
     mempty = MyList []
     mappend (MyList x) (MyList y) = MyList (x ++ y)
