on 3cf8564 help sign in
text/Data/Text.hs
1644 lines 56 kB history raw
1{-# LANGUAGE BangPatterns, CPP, MagicHash, Rank2Types, UnboxedTuples #-}
2{-# OPTIONS_GHC -fno-warn-orphans #-}
3#if __GLASGOW_HASKELL__ >= 702
4{-# LANGUAGE Trustworthy #-}
5#endif
7-- |
8-- Module : Data.Text
9-- Copyright : (c) 2009, 2010, 2011, 2012 Bryan O'Sullivan,
10-- (c) 2009 Duncan Coutts,
11-- (c) 2008, 2009 Tom Harper
12--
13-- License : BSD-style
14-- Maintainer : bos@serpentine.com, rtomharper@googlemail.com,
15-- duncan@haskell.org
16-- Stability : experimental
17-- Portability : GHC
18--
19-- A time and space-efficient implementation of Unicode text.
20-- Suitable for performance critical use, both in terms of large data
21-- quantities and high speed.
22--
23-- /Note/: Read below the synopsis for important notes on the use of
24-- this module.
25--
26-- This module is intended to be imported @qualified@, to avoid name
27-- clashes with "Prelude" functions, e.g.
28--
29-- > import qualified Data.Text as T
30--
31-- To use an extended and very rich family of functions for working
32-- with Unicode text (including normalization, regular expressions,
33-- non-standard encodings, text breaking, and locales), see the
34-- @text-icu@ package: <http://hackage.haskell.org/package/text-icu>
36module Data.Text
37 (
38 -- * Strict vs lazy types
39 -- $strict
41 -- * Acceptable data
42 -- $replacement
44 -- * Fusion
45 -- $fusion
47 -- * Types
48 Text
50 -- * Creation and elimination
51 , pack
52 , unpack
53 , singleton
54 , empty
56 -- * Basic interface
57 , cons
58 , snoc
59 , append
60 , uncons
61 , head
62 , last
63 , tail
64 , init
65 , null
66 , length
67 , compareLength
69 -- * Transformations
70 , map
71 , intercalate
72 , intersperse
73 , transpose
74 , reverse
75 , replace
76 , replace2
78 -- ** Case conversion
79 -- $case
80 , toCaseFold
81 , toLower
82 , toUpper
83 , toTitle
85 -- ** Justification
86 , justifyLeft
87 , justifyRight
88 , center
90 -- * Folds
91 , foldl
92 , foldl'
93 , foldl1
94 , foldl1'
95 , foldr
96 , foldr1
98 -- ** Special folds
99 , concat
100 , concatMap
101 , any
102 , all
103 , maximum
104 , minimum
106 -- * Construction
108 -- ** Scans
109 , scanl
110 , scanl1
111 , scanr
112 , scanr1
114 -- ** Accumulating maps
115 , mapAccumL
116 , mapAccumR
118 -- ** Generation and unfolding
119 , replicate
120 , unfoldr
121 , unfoldrN
123 -- * Substrings
125 -- ** Breaking strings
126 , take
127 , drop
128 , takeWhile
129 , dropWhile
130 , dropWhileEnd
131 , dropAround
132 , strip
133 , stripStart
134 , stripEnd
135 , splitAt
136 , breakOn
137 , breakOnEnd
138 , break
139 , span
140 , group
141 , groupBy
142 , inits
143 , tails
145 -- ** Breaking into many substrings
146 -- $split
147 , splitOn
148 , split
149 , chunksOf
151 -- ** Breaking into lines and words
152 , lines
153 --, lines'
154 , words
155 , unlines
156 , unwords
158 -- * Predicates
159 , isPrefixOf
160 , isSuffixOf
161 , isInfixOf
163 -- ** View patterns
164 , stripPrefix
165 , stripSuffix
166 , commonPrefixes
168 -- * Searching
169 , filter
170 , breakOnAll
171 , find
172 , partition
174 -- , findSubstring
176 -- * Indexing
177 -- $index
178 , index
179 , findIndex
180 , count
182 -- * Zipping
183 , zip
184 , zipWith
186 -- -* Ordered text
187 -- , sort
189 -- * Low level operations
190 , copy
191 ) where
193import Prelude (Char, Bool(..), Int, Maybe(..), String,
194 Eq(..), Ord(..), Ordering(..), (++),
195 Read(..), Show(..),
196 (&&), (||), (+), (-), (.), ($), ($!), (>>), (*),
197 maxBound, not, return, otherwise, quot)
198#if defined(HAVE_DEEPSEQ)
199import Control.DeepSeq (NFData)
200#endif
201#if defined(ASSERTS)
202import Control.Exception (assert)
203#endif
204import Data.Char (isSpace)
205import Data.Data (Data(gfoldl, toConstr, gunfold, dataTypeOf))
206import Data.Data (mkNoRepType)
207import Control.Monad (foldM)
208import qualified Data.Text.Array as A
209import qualified Data.List as L
210import Data.Monoid (Monoid(..))
211import Data.String (IsString(..))
212import qualified Data.Text.Fusion as S
213import qualified Data.Text.Fusion.Common as S
214import Data.Text.Fusion (stream, reverseStream, unstream)
215import Data.Text.Private (span_)
216import Data.Text.Internal (Text(..), empty, firstf, safe, text, textP)
217import qualified Prelude as P
218import Data.Text.Unsafe (Iter(..), iter, iter_, lengthWord16, reverseIter,
219 unsafeHead, unsafeTail)
220import Data.Text.UnsafeChar (unsafeChr)
221import qualified Data.Text.Util as U
222import qualified Data.Text.Encoding.Utf16 as U16
223import Data.Text.Search (indices)
224#if defined(__HADDOCK__)
225import Data.ByteString (ByteString)
226import qualified Data.Text.Lazy as L
227import Data.Int (Int64)
228#endif
229#if __GLASGOW_HASKELL__ >= 702
230import qualified GHC.CString as GHC
231#else
232import qualified GHC.Base as GHC
233#endif
234import GHC.Prim (Addr#)
236-- $strict
237--
238-- This package provides both strict and lazy 'Text' types. The
239-- strict type is provided by the 'Data.Text' package, while the lazy
240-- type is provided by the 'Data.Text.Lazy' package. Internally, the
241-- lazy @Text@ type consists of a list of strict chunks.
242--
243-- The strict 'Text' type requires that an entire string fit into
244-- memory at once. The lazy @Text@ type is capable of streaming
245-- strings that are larger than memory using a small memory footprint.
246-- In many cases, the overhead of chunked streaming makes the lazy
247-- @Text@ type slower than its strict counterpart, but this is not
248-- always the case. Sometimes, the time complexity of a function in
249-- one module may be different from the other, due to their differing
250-- internal structures.
251--
252-- Each module provides an almost identical API, with the main
253-- difference being that the strict module uses 'Int' values for
254-- lengths and counts, while the lazy module uses 'Int64' lengths.
256-- $replacement
257--
258-- A 'Text' value is a sequence of Unicode scalar values, as defined
259-- in &#xa7;3.9, definition D76 of the Unicode 5.2 standard:
260-- <http://www.unicode.org/versions/Unicode5.2.0/ch03.pdf#page=35>. As
261-- such, a 'Text' cannot contain values in the range U+D800 to U+DFFF
262-- inclusive. Haskell implementations admit all Unicode code points
263-- (&#xa7;3.4, definition D10) as 'Char' values, including code points
264-- from this invalid range. This means that there are some 'Char'
265-- values that are not valid Unicode scalar values, and the functions
266-- in this module must handle those cases.
267--
268-- Within this module, many functions construct a 'Text' from one or
269-- more 'Char' values. Those functions will substitute 'Char' values
270-- that are not valid Unicode scalar values with the replacement
271-- character \"&#xfffd;\" (U+FFFD). Functions that perform this
272-- inspection and replacement are documented with the phrase
273-- \"Performs replacement on invalid scalar values\".
274--
275-- (One reason for this policy of replacement is that internally, a
276-- 'Text' value is represented as packed UTF-16 data. Values in the
277-- range U+D800 through U+DFFF are used by UTF-16 to denote surrogate
278-- code points, and so cannot be represented. The functions replace
279-- invalid scalar values, instead of dropping them, as a security
280-- measure. For details, see Unicode Technical Report 36, &#xa7;3.5:
281-- <http://unicode.org/reports/tr36/#Deletion_of_Noncharacters>)
283-- $fusion
284--
285-- Most of the functions in this module are subject to /fusion/,
286-- meaning that a pipeline of such functions will usually allocate at
287-- most one 'Text' value.
288--
289-- As an example, consider the following pipeline:
290--
291-- > import Data.Text as T
292-- > import Data.Text.Encoding as E
293-- > import Data.ByteString (ByteString)
294-- >
295-- > countChars :: ByteString -> Int
296-- > countChars = T.length . T.toUpper . E.decodeUtf8
297--
298-- From the type signatures involved, this looks like it should
299-- allocate one 'ByteString' value, and two 'Text' values. However,
300-- when a module is compiled with optimisation enabled under GHC, the
301-- two intermediate 'Text' values will be optimised away, and the
302-- function will be compiled down to a single loop over the source
303-- 'ByteString'.
304--
305-- Functions that can be fused by the compiler are documented with the
306-- phrase \"Subject to fusion\".
308instance Eq Text where
309 Text arrA offA lenA == Text arrB offB lenB
310 | lenA == lenB = A.equal arrA offA arrB offB lenA
311 | otherwise = False
312 {-# INLINE (==) #-}
314instance Ord Text where
315 compare = compareText
317instance Show Text where
318 showsPrec p ps r = showsPrec p (unpack ps) r
320instance Read Text where
321 readsPrec p str = [(pack x,y) | (x,y) <- readsPrec p str]
323instance Monoid Text where
324 mempty = empty
325 mappend = append
326 mconcat = concat
328instance IsString Text where
329 fromString = pack
331#if defined(HAVE_DEEPSEQ)
332instance NFData Text
333#endif
335-- This instance preserves data abstraction at the cost of inefficiency.
336-- We omit reflection services for the sake of data abstraction.
337--
338-- This instance was created by copying the behavior of Data.Set and
339-- Data.Map. If you feel a mistake has been made, please feel free to
340-- submit improvements.
341--
342-- Original discussion is archived here:
344-- "could we get a Data instance for Data.Text.Text?"
345-- http://groups.google.com/group/haskell-cafe/browse_thread/thread/b5bbb1b28a7e525d/0639d46852575b93
347instance Data Text where
348 gfoldl f z txt = z pack `f` (unpack txt)
349 toConstr _ = P.error "Data.Text.Text.toConstr"
350 gunfold _ _ = P.error "Data.Text.Text.gunfold"
351 dataTypeOf _ = mkNoRepType "Data.Text.Text"
353-- | /O(n)/ Compare two 'Text' values lexicographically.
354compareText :: Text -> Text -> Ordering
355compareText ta@(Text _arrA _offA lenA) tb@(Text _arrB _offB lenB)
356 | lenA == 0 && lenB == 0 = EQ
357 | otherwise = go 0 0
358 where
359 go !i !j
360 | i >= lenA || j >= lenB = compare lenA lenB
361 | a < b = LT
362 | a > b = GT
363 | otherwise = go (i+di) (j+dj)
364 where Iter a di = iter ta i
365 Iter b dj = iter tb j
367-- -----------------------------------------------------------------------------
368-- * Conversion to/from 'Text'
370-- | /O(n)/ Convert a 'String' into a 'Text'. Subject to
371-- fusion. Performs replacement on invalid scalar values.
372pack :: String -> Text
373pack = unstream . S.map safe . S.streamList
374{-# INLINE [1] pack #-}
376-- | /O(n)/ Convert a Text into a String. Subject to fusion.
377unpack :: Text -> String
378unpack = S.unstreamList . stream
379{-# INLINE [1] unpack #-}
381-- | /O(n)/ Convert a literal string into a Text. Subject to fusion.
382unpackCString# :: Addr# -> Text
383unpackCString# addr# = unstream (S.streamCString# addr#)
384{-# NOINLINE unpackCString# #-}
386{-# RULES "TEXT literal" forall a.
387 unstream (S.map safe (S.streamList (GHC.unpackCString# a)))
388 = unpackCString# a #-}
390{-# RULES "TEXT literal UTF8" forall a.
391 unstream (S.map safe (S.streamList (GHC.unpackCStringUtf8# a)))
392 = unpackCString# a #-}
394-- | /O(1)/ Convert a character into a Text. Subject to fusion.
395-- Performs replacement on invalid scalar values.
396singleton :: Char -> Text
397singleton = unstream . S.singleton . safe
398{-# INLINE [1] singleton #-}
400-- -----------------------------------------------------------------------------
401-- * Basic functions
403-- | /O(n)/ Adds a character to the front of a 'Text'. This function
404-- is more costly than its 'List' counterpart because it requires
405-- copying a new array. Subject to fusion. Performs replacement on
406-- invalid scalar values.
407cons :: Char -> Text -> Text
408cons c t = unstream (S.cons (safe c) (stream t))
409{-# INLINE cons #-}
411infixr 5 `cons`
413-- | /O(n)/ Adds a character to the end of a 'Text'. This copies the
414-- entire array in the process, unless fused. Subject to fusion.
415-- Performs replacement on invalid scalar values.
416snoc :: Text -> Char -> Text
417snoc t c = unstream (S.snoc (stream t) (safe c))
418{-# INLINE snoc #-}
420-- | /O(n)/ Appends one 'Text' to the other by copying both of them
421-- into a new 'Text'. Subject to fusion.
422append :: Text -> Text -> Text
423append a@(Text arr1 off1 len1) b@(Text arr2 off2 len2)
424 | len1 == 0 = b
425 | len2 == 0 = a
426 | len > 0 = Text (A.run x) 0 len
427 | otherwise = overflowError "append"
428 where
429 len = len1+len2
430 x = do
431 arr <- A.new len
432 A.copyI arr 0 arr1 off1 len1
433 A.copyI arr len1 arr2 off2 len
434 return arr
435{-# INLINE append #-}
437{-# RULES
438"TEXT append -> fused" [~1] forall t1 t2.
439 append t1 t2 = unstream (S.append (stream t1) (stream t2))
440"TEXT append -> unfused" [1] forall t1 t2.
441 unstream (S.append (stream t1) (stream t2)) = append t1 t2
442 #-}
444-- | /O(1)/ Returns the first character of a 'Text', which must be
445-- non-empty. Subject to fusion.
446head :: Text -> Char
447head t = S.head (stream t)
448{-# INLINE head #-}
450-- | /O(1)/ Returns the first character and rest of a 'Text', or
451-- 'Nothing' if empty. Subject to fusion.
452uncons :: Text -> Maybe (Char, Text)
453uncons t@(Text arr off len)
454 | len <= 0 = Nothing
455 | otherwise = Just (c, textP arr (off+d) (len-d))
456 where Iter c d = iter t 0
457{-# INLINE [1] uncons #-}
459-- | Lifted from Control.Arrow and specialized.
460second :: (b -> c) -> (a,b) -> (a,c)
461second f (a, b) = (a, f b)
463-- | /O(1)/ Returns the last character of a 'Text', which must be
464-- non-empty. Subject to fusion.
465last :: Text -> Char
466last (Text arr off len)
467 | len <= 0 = emptyError "last"
468 | n < 0xDC00 || n > 0xDFFF = unsafeChr n
469 | otherwise = U16.chr2 n0 n
470 where n = A.unsafeIndex arr (off+len-1)
471 n0 = A.unsafeIndex arr (off+len-2)
472{-# INLINE [1] last #-}
474{-# RULES
475"TEXT last -> fused" [~1] forall t.
476 last t = S.last (stream t)
477"TEXT last -> unfused" [1] forall t.
478 S.last (stream t) = last t
479 #-}
481-- | /O(1)/ Returns all characters after the head of a 'Text', which
482-- must be non-empty. Subject to fusion.
483tail :: Text -> Text
484tail t@(Text arr off len)
485 | len <= 0 = emptyError "tail"
486 | otherwise = textP arr (off+d) (len-d)
487 where d = iter_ t 0
488{-# INLINE [1] tail #-}
490{-# RULES
491"TEXT tail -> fused" [~1] forall t.
492 tail t = unstream (S.tail (stream t))
493"TEXT tail -> unfused" [1] forall t.
494 unstream (S.tail (stream t)) = tail t
495 #-}
497-- | /O(1)/ Returns all but the last character of a 'Text', which must
498-- be non-empty. Subject to fusion.
499init :: Text -> Text
500init (Text arr off len) | len <= 0 = emptyError "init"
501 | n >= 0xDC00 && n <= 0xDFFF = textP arr off (len-2)
502 | otherwise = textP arr off (len-1)
503 where
504 n = A.unsafeIndex arr (off+len-1)
505{-# INLINE [1] init #-}
507{-# RULES
508"TEXT init -> fused" [~1] forall t.
509 init t = unstream (S.init (stream t))
510"TEXT init -> unfused" [1] forall t.
511 unstream (S.init (stream t)) = init t
512 #-}
514-- | /O(1)/ Tests whether a 'Text' is empty or not. Subject to
515-- fusion.
516null :: Text -> Bool
517null (Text _arr _off len) =
518#if defined(ASSERTS)
519 assert (len >= 0) $
520#endif
521 len <= 0
522{-# INLINE [1] null #-}
524{-# RULES
525"TEXT null -> fused" [~1] forall t.
526 null t = S.null (stream t)
527"TEXT null -> unfused" [1] forall t.
528 S.null (stream t) = null t
529 #-}
531-- | /O(1)/ Tests whether a 'Text' contains exactly one character.
532-- Subject to fusion.
533isSingleton :: Text -> Bool
534isSingleton = S.isSingleton . stream
535{-# INLINE isSingleton #-}
537-- | /O(n)/ Returns the number of characters in a 'Text'.
538-- Subject to fusion.
539length :: Text -> Int
540length t = S.length (stream t)
541{-# INLINE length #-}
543-- | /O(n)/ Compare the count of characters in a 'Text' to a number.
544-- Subject to fusion.
545--
546-- This function gives the same answer as comparing against the result
547-- of 'length', but can short circuit if the count of characters is
548-- greater than the number, and hence be more efficient.
549compareLength :: Text -> Int -> Ordering
550compareLength t n = S.compareLengthI (stream t) n
551{-# INLINE [1] compareLength #-}
553{-# RULES
554"TEXT compareN/length -> compareLength" [~1] forall t n.
555 compare (length t) n = compareLength t n
556 #-}
558{-# RULES
559"TEXT ==N/length -> compareLength/==EQ" [~1] forall t n.
560 (==) (length t) n = compareLength t n == EQ
561 #-}
563{-# RULES
564"TEXT /=N/length -> compareLength//=EQ" [~1] forall t n.
565 (/=) (length t) n = compareLength t n /= EQ
566 #-}
568{-# RULES
569"TEXT <N/length -> compareLength/==LT" [~1] forall t n.
570 (<) (length t) n = compareLength t n == LT
571 #-}
573{-# RULES
574"TEXT <=N/length -> compareLength//=GT" [~1] forall t n.
575 (<=) (length t) n = compareLength t n /= GT
576 #-}
578{-# RULES
579"TEXT >N/length -> compareLength/==GT" [~1] forall t n.
580 (>) (length t) n = compareLength t n == GT
581 #-}
583{-# RULES
584"TEXT >=N/length -> compareLength//=LT" [~1] forall t n.
585 (>=) (length t) n = compareLength t n /= LT
586 #-}
588-- -----------------------------------------------------------------------------
589-- * Transformations
590-- | /O(n)/ 'map' @f@ @t@ is the 'Text' obtained by applying @f@ to
591-- each element of @t@. Subject to fusion. Performs replacement on
592-- invalid scalar values.
593map :: (Char -> Char) -> Text -> Text
594map f t = unstream (S.map (safe . f) (stream t))
595{-# INLINE [1] map #-}
597-- | /O(n)/ The 'intercalate' function takes a 'Text' and a list of
598-- 'Text's and concatenates the list after interspersing the first
599-- argument between each element of the list.
600intercalate :: Text -> [Text] -> Text
601intercalate t = concat . (U.intersperse t)
602{-# INLINE intercalate #-}
604-- | /O(n)/ The 'intersperse' function takes a character and places it
605-- between the characters of a 'Text'. Subject to fusion. Performs
606-- replacement on invalid scalar values.
607intersperse :: Char -> Text -> Text
608intersperse c t = unstream (S.intersperse (safe c) (stream t))
609{-# INLINE intersperse #-}
611-- | /O(n)/ Reverse the characters of a string. Subject to fusion.
612reverse :: Text -> Text
613reverse t = S.reverse (stream t)
614{-# INLINE reverse #-}
616-- | /O(m+n)/ Replace every occurrence of one substring with another.
617--
618-- In (unlikely) bad cases, this function's time complexity degrades
619-- towards /O(n*m)/.
620replace :: Text -- ^ Text to search for
621 -> Text -- ^ Replacement text
622 -> Text -- ^ Input text
623 -> Text
624replace s d = intercalate d . splitOn s
625{-# INLINE replace #-}
627replace2 :: Text -> Text -> Text -> Text
628replace2 needle@(Text _ _ neeLen)
629 r@(Text repArr repOff repLen)
630 haystack@(Text hayArr hayOff hayLen)
631 | neeLen == 0 = emptyError "replace2"
632 | len < 0 = overflowError "replace2"
633 | len == 0 = empty
634 | L.null ixs = haystack
635 | otherwise = Text (A.run x) 0 len
636 where
637 ixs = indices needle haystack
638 cnt = L.length ixs
639 len = hayLen - (neeLen - repLen) * cnt
640 x = do
641 marr <- A.new len
642 let loop is0@(i:is) o d = do
643 let d0 = d + i - o
644 d1 = d0 + repLen
645 A.copyI marr d hayArr (hayOff+o) d0
646 A.copyI marr d0 repArr repOff d1
647 loop is (i + neeLen) d1
648 loop [] o d = A.copyI marr d hayArr (hayOff+o) len
649 loop ixs 0 0
650 return marr
652-- ----------------------------------------------------------------------------
653-- ** Case conversions (folds)
655-- $case
656--
657-- When case converting 'Text' values, do not use combinators like
658-- @map toUpper@ to case convert each character of a string
659-- individually, as this gives incorrect results according to the
660-- rules of some writing systems. The whole-string case conversion
661-- functions from this module, such as @toUpper@, obey the correct
662-- case conversion rules. As a result, these functions may map one
663-- input character to two or three output characters. For examples,
664-- see the documentation of each function.
665--
666-- /Note/: In some languages, case conversion is a locale- and
667-- context-dependent operation. The case conversion functions in this
668-- module are /not/ locale sensitive. Programs that require locale
669-- sensitivity should use appropriate versions of the case mapping
670-- functions from the @text-icu@ package:
671-- <http://hackage.haskell.org/package/text-icu>
673-- | /O(n)/ Convert a string to folded case. Subject to fusion.
674--
675-- This function is mainly useful for performing caseless (also known
676-- as case insensitive) string comparisons.
677--
678-- A string @x@ is a caseless match for a string @y@ if and only if:
679--
680-- @toCaseFold x == toCaseFold y@
681--
682-- The result string may be longer than the input string, and may
683-- differ from applying 'toLower' to the input string. For instance,
684-- the Armenian small ligature \"&#xfb13;\" (men now, U+FB13) is case
685-- folded to the sequence \"&#x574;\" (men, U+0574) followed by
686-- \"&#x576;\" (now, U+0576), while the Greek \"&#xb5;\" (micro sign,
687-- U+00B5) is case folded to \"&#x3bc;\" (small letter mu, U+03BC)
688-- instead of itself.
689toCaseFold :: Text -> Text
690toCaseFold t = unstream (S.toCaseFold (stream t))
691{-# INLINE [0] toCaseFold #-}
693-- | /O(n)/ Convert a string to lower case, using simple case
694-- conversion. Subject to fusion.
695--
696-- The result string may be longer than the input string. For
697-- instance, \"&#x130;\" (Latin capital letter I with dot above,
698-- U+0130) maps to the sequence \"i\" (Latin small letter i, U+0069)
699-- followed by \" &#x307;\" (combining dot above, U+0307).
700toLower :: Text -> Text
701toLower t = unstream (S.toLower (stream t))
702{-# INLINE toLower #-}
704-- | /O(n)/ Convert a string to upper case, using simple case
705-- conversion. Subject to fusion.
706--
707-- The result string may be longer than the input string. For
708-- instance, the German \"&#xdf;\" (eszett, U+00DF) maps to the
709-- two-letter sequence \"SS\".
710toUpper :: Text -> Text
711toUpper t = unstream (S.toUpper (stream t))
712{-# INLINE toUpper #-}
714-- | /O(n)/ Convert a string to title case, using simple case
715-- conversion. Subject to fusion.
716--
717-- The first letter of the input is converted to title case, as is
718-- every subsequent letter that immediately follows a non-letter.
719-- Every letter that immediately follows another letter is converted
720-- to lower case.
721--
722-- The result string may be longer than the input string. For example,
723-- the Latin small ligature &#xfb02; (U+FB02) is converted to the
724-- sequence Latin capital letter F (U+0046) followed by Latin small
725-- letter l (U+006C).
726--
727-- /Note/: this function does not take language or culture specific
728-- rules into account. For instance, in English, different style
729-- guides disagree on whether the book name \"The Hill of the Red
730-- Fox\" is correctly title cased&#x2014;but this function will
731-- capitalize /every/ word.
732toTitle :: Text -> Text
733toTitle t = unstream (S.toTitle (stream t))
734{-# INLINE toTitle #-}
736-- | /O(n)/ Left-justify a string to the given length, using the
737-- specified fill character on the right. Subject to fusion.
738-- Performs replacement on invalid scalar values.
739--
740-- Examples:
741--
742-- > justifyLeft 7 'x' "foo" == "fooxxxx"
743-- > justifyLeft 3 'x' "foobar" == "foobar"
744justifyLeft :: Int -> Char -> Text -> Text
745justifyLeft k c t
746 | len >= k = t
747 | otherwise = t `append` replicateChar (k-len) c
748 where len = length t
749{-# INLINE [1] justifyLeft #-}
751{-# RULES
752"TEXT justifyLeft -> fused" [~1] forall k c t.
753 justifyLeft k c t = unstream (S.justifyLeftI k c (stream t))
754"TEXT justifyLeft -> unfused" [1] forall k c t.
755 unstream (S.justifyLeftI k c (stream t)) = justifyLeft k c t
756 #-}
758-- | /O(n)/ Right-justify a string to the given length, using the
759-- specified fill character on the left. Performs replacement on
760-- invalid scalar values.
761--
762-- Examples:
763--
764-- > justifyRight 7 'x' "bar" == "xxxxbar"
765-- > justifyRight 3 'x' "foobar" == "foobar"
766justifyRight :: Int -> Char -> Text -> Text
767justifyRight k c t
768 | len >= k = t
769 | otherwise = replicateChar (k-len) c `append` t
770 where len = length t
771{-# INLINE justifyRight #-}
773-- | /O(n)/ Center a string to the given length, using the specified
774-- fill character on either side. Performs replacement on invalid
775-- scalar values.
776--
777-- Examples:
778--
779-- > center 8 'x' "HS" = "xxxHSxxx"
780center :: Int -> Char -> Text -> Text
781center k c t
782 | len >= k = t
783 | otherwise = replicateChar l c `append` t `append` replicateChar r c
784 where len = length t
785 d = k - len
786 r = d `quot` 2
787 l = d - r
788{-# INLINE center #-}
790-- | /O(n)/ The 'transpose' function transposes the rows and columns
791-- of its 'Text' argument. Note that this function uses 'pack',
792-- 'unpack', and the list version of transpose, and is thus not very
793-- efficient.
794transpose :: [Text] -> [Text]
795transpose ts = P.map pack (L.transpose (P.map unpack ts))
797-- -----------------------------------------------------------------------------
798-- * Reducing 'Text's (folds)
800-- | /O(n)/ 'foldl', applied to a binary operator, a starting value
801-- (typically the left-identity of the operator), and a 'Text',
802-- reduces the 'Text' using the binary operator, from left to right.
803-- Subject to fusion.
804foldl :: (a -> Char -> a) -> a -> Text -> a
805foldl f z t = S.foldl f z (stream t)
806{-# INLINE foldl #-}
808-- | /O(n)/ A strict version of 'foldl'. Subject to fusion.
809foldl' :: (a -> Char -> a) -> a -> Text -> a
810foldl' f z t = S.foldl' f z (stream t)
811{-# INLINE foldl' #-}
813-- | /O(n)/ A variant of 'foldl' that has no starting value argument,
814-- and thus must be applied to a non-empty 'Text'. Subject to fusion.
815foldl1 :: (Char -> Char -> Char) -> Text -> Char
816foldl1 f t = S.foldl1 f (stream t)
817{-# INLINE foldl1 #-}
819-- | /O(n)/ A strict version of 'foldl1'. Subject to fusion.
820foldl1' :: (Char -> Char -> Char) -> Text -> Char
821foldl1' f t = S.foldl1' f (stream t)
822{-# INLINE foldl1' #-}
824-- | /O(n)/ 'foldr', applied to a binary operator, a starting value
825-- (typically the right-identity of the operator), and a 'Text',
826-- reduces the 'Text' using the binary operator, from right to left.
827-- Subject to fusion.
828foldr :: (Char -> a -> a) -> a -> Text -> a
829foldr f z t = S.foldr f z (stream t)
830{-# INLINE foldr #-}
832-- | /O(n)/ A variant of 'foldr' that has no starting value argument,
833-- and thus must be applied to a non-empty 'Text'. Subject to
834-- fusion.
835foldr1 :: (Char -> Char -> Char) -> Text -> Char
836foldr1 f t = S.foldr1 f (stream t)
837{-# INLINE foldr1 #-}
839-- -----------------------------------------------------------------------------
840-- ** Special folds
842-- | /O(n)/ Concatenate a list of 'Text's.
843concat :: [Text] -> Text
844concat ts = case ts' of
845 [] -> empty
846 [t] -> t
847 _ -> Text (A.run go) 0 len
848 where
849 ts' = L.filter (not . null) ts
850 len = sumP "concat" $ L.map lengthWord16 ts'
851 go = do
852 arr <- A.new len
853 let step i (Text a o l) =
854 let !j = i + l in A.copyI arr i a o j >> return j
855 foldM step 0 ts' >> return arr
857-- | /O(n)/ Map a function over a 'Text' that results in a 'Text', and
858-- concatenate the results.
859concatMap :: (Char -> Text) -> Text -> Text
860concatMap f = concat . foldr ((:) . f) []
861{-# INLINE concatMap #-}
863-- | /O(n)/ 'any' @p@ @t@ determines whether any character in the
864-- 'Text' @t@ satisifes the predicate @p@. Subject to fusion.
865any :: (Char -> Bool) -> Text -> Bool
866any p t = S.any p (stream t)
867{-# INLINE any #-}
869-- | /O(n)/ 'all' @p@ @t@ determines whether all characters in the
870-- 'Text' @t@ satisify the predicate @p@. Subject to fusion.
871all :: (Char -> Bool) -> Text -> Bool
872all p t = S.all p (stream t)
873{-# INLINE all #-}
875-- | /O(n)/ 'maximum' returns the maximum value from a 'Text', which
876-- must be non-empty. Subject to fusion.
877maximum :: Text -> Char
878maximum t = S.maximum (stream t)
879{-# INLINE maximum #-}
881-- | /O(n)/ 'minimum' returns the minimum value from a 'Text', which
882-- must be non-empty. Subject to fusion.
883minimum :: Text -> Char
884minimum t = S.minimum (stream t)
885{-# INLINE minimum #-}
887-- -----------------------------------------------------------------------------
888-- * Building 'Text's
890-- | /O(n)/ 'scanl' is similar to 'foldl', but returns a list of
891-- successive reduced values from the left. Subject to fusion.
892-- Performs replacement on invalid scalar values.
893--
894-- > scanl f z [x1, x2, ...] == [z, z `f` x1, (z `f` x1) `f` x2, ...]
895--
896-- Note that
897--
898-- > last (scanl f z xs) == foldl f z xs.
899scanl :: (Char -> Char -> Char) -> Char -> Text -> Text
900scanl f z t = unstream (S.scanl g z (stream t))
901 where g a b = safe (f a b)
902{-# INLINE scanl #-}
904-- | /O(n)/ 'scanl1' is a variant of 'scanl' that has no starting
905-- value argument. Subject to fusion. Performs replacement on
906-- invalid scalar values.
907--
908-- > scanl1 f [x1, x2, ...] == [x1, x1 `f` x2, ...]
909scanl1 :: (Char -> Char -> Char) -> Text -> Text
910scanl1 f t | null t = empty
911 | otherwise = scanl f (unsafeHead t) (unsafeTail t)
912{-# INLINE scanl1 #-}
914-- | /O(n)/ 'scanr' is the right-to-left dual of 'scanl'. Performs
915-- replacement on invalid scalar values.
916--
917-- > scanr f v == reverse . scanl (flip f) v . reverse
918scanr :: (Char -> Char -> Char) -> Char -> Text -> Text
919scanr f z = S.reverse . S.reverseScanr g z . reverseStream
920 where g a b = safe (f a b)
921{-# INLINE scanr #-}
923-- | /O(n)/ 'scanr1' is a variant of 'scanr' that has no starting
924-- value argument. Subject to fusion. Performs replacement on
925-- invalid scalar values.
926scanr1 :: (Char -> Char -> Char) -> Text -> Text
927scanr1 f t | null t = empty
928 | otherwise = scanr f (last t) (init t)
929{-# INLINE scanr1 #-}
931-- | /O(n)/ Like a combination of 'map' and 'foldl''. Applies a
932-- function to each element of a 'Text', passing an accumulating
933-- parameter from left to right, and returns a final 'Text'. Performs
934-- replacement on invalid scalar values.
935mapAccumL :: (a -> Char -> (a,Char)) -> a -> Text -> (a, Text)
936mapAccumL f z0 = S.mapAccumL g z0 . stream
937 where g a b = second safe (f a b)
938{-# INLINE mapAccumL #-}
940-- | The 'mapAccumR' function behaves like a combination of 'map' and
941-- a strict 'foldr'; it applies a function to each element of a
942-- 'Text', passing an accumulating parameter from right to left, and
943-- returning a final value of this accumulator together with the new
944-- 'Text'.
945-- Performs replacement on invalid scalar values.
946mapAccumR :: (a -> Char -> (a,Char)) -> a -> Text -> (a, Text)
947mapAccumR f z0 = second reverse . S.mapAccumL g z0 . reverseStream
948 where g a b = second safe (f a b)
949{-# INLINE mapAccumR #-}
951-- -----------------------------------------------------------------------------
952-- ** Generating and unfolding 'Text's
954-- | /O(n*m)/ 'replicate' @n@ @t@ is a 'Text' consisting of the input
955-- @t@ repeated @n@ times.
956replicate :: Int -> Text -> Text
957replicate n t@(Text a o l)
958 | n <= 0 || l <= 0 = empty
959 | n == 1 = t
960 | isSingleton t = replicateChar n (unsafeHead t)
961 | n <= maxBound `quot` l = Text (A.run x) 0 len
962 | otherwise = overflowError "replicate"
963 where
964 len = l * n
965 x = do
966 arr <- A.new len
967 let loop !d !i | i >= n = return arr
968 | otherwise = let m = d + l
969 in A.copyI arr d a o m >> loop m (i+1)
970 loop 0 0
971{-# INLINE [1] replicate #-}
973{-# RULES
974"TEXT replicate/singleton -> replicateChar" [~1] forall n c.
975 replicate n (singleton c) = replicateChar n c
976 #-}
978-- | /O(n)/ 'replicateChar' @n@ @c@ is a 'Text' of length @n@ with @c@ the
979-- value of every element. Subject to fusion.
980replicateChar :: Int -> Char -> Text
981replicateChar n c = unstream (S.replicateCharI n (safe c))
982{-# INLINE replicateChar #-}
984-- | /O(n)/, where @n@ is the length of the result. The 'unfoldr'
985-- function is analogous to the List 'L.unfoldr'. 'unfoldr' builds a
986-- 'Text' from a seed value. The function takes the element and
987-- returns 'Nothing' if it is done producing the 'Text', otherwise
988-- 'Just' @(a,b)@. In this case, @a@ is the next 'Char' in the
989-- string, and @b@ is the seed value for further production. Subject
990-- to fusion. Performs replacement on invalid scalar values.
991unfoldr :: (a -> Maybe (Char,a)) -> a -> Text
992unfoldr f s = unstream (S.unfoldr (firstf safe . f) s)
993{-# INLINE unfoldr #-}
995-- | /O(n)/ Like 'unfoldr', 'unfoldrN' builds a 'Text' from a seed
996-- value. However, the length of the result should be limited by the
997-- first argument to 'unfoldrN'. This function is more efficient than
998-- 'unfoldr' when the maximum length of the result is known and
999-- correct, otherwise its performance is similar to 'unfoldr'. Subject
1000-- to fusion. Performs replacement on invalid scalar values.
1001unfoldrN :: Int -> (a -> Maybe (Char,a)) -> a -> Text
1002unfoldrN n f s = unstream (S.unfoldrN n (firstf safe . f) s)
1003{-# INLINE unfoldrN #-}
1005-- -----------------------------------------------------------------------------
1006-- * Substrings
1008-- | /O(n)/ 'take' @n@, applied to a 'Text', returns the prefix of the
1009-- 'Text' of length @n@, or the 'Text' itself if @n@ is greater than
1010-- the length of the Text. Subject to fusion.
1011take :: Int -> Text -> Text
1012take n t@(Text arr off len)
1013 | n <= 0 = empty
1014 | n >= len = t
1015 | otherwise = Text arr off (loop 0 0)
1016 where
1017 loop !i !cnt
1018 | i >= len || cnt >= n = i
1019 | otherwise = loop (i+d) (cnt+1)
1020 where d = iter_ t i
1021{-# INLINE [1] take #-}
1023{-# RULES
1024"TEXT take -> fused" [~1] forall n t.
1025 take n t = unstream (S.take n (stream t))
1026"TEXT take -> unfused" [1] forall n t.
1027 unstream (S.take n (stream t)) = take n t
1028 #-}
1030-- | /O(n)/ 'drop' @n@, applied to a 'Text', returns the suffix of the
1031-- 'Text' after the first @n@ characters, or the empty 'Text' if @n@
1032-- is greater than the length of the 'Text'. Subject to fusion.
1033drop :: Int -> Text -> Text
1034drop n t@(Text arr off len)
1035 | n <= 0 = t
1036 | n >= len = empty
1037 | otherwise = loop 0 0
1038 where loop !i !cnt
1039 | i >= len || cnt >= n = Text arr (off+i) (len-i)
1040 | otherwise = loop (i+d) (cnt+1)
1041 where d = iter_ t i
1042{-# INLINE [1] drop #-}
1044{-# RULES
1045"TEXT drop -> fused" [~1] forall n t.
1046 drop n t = unstream (S.drop n (stream t))
1047"TEXT drop -> unfused" [1] forall n t.
1048 unstream (S.drop n (stream t)) = drop n t
1049 #-}
1051-- | /O(n)/ 'takeWhile', applied to a predicate @p@ and a 'Text',
1052-- returns the longest prefix (possibly empty) of elements that
1053-- satisfy @p@. Subject to fusion.
1054takeWhile :: (Char -> Bool) -> Text -> Text
1055takeWhile p t@(Text arr off len) = loop 0
1056 where loop !i | i >= len = t
1057 | p c = loop (i+d)
1058 | otherwise = textP arr off i
1059 where Iter c d = iter t i
1060{-# INLINE [1] takeWhile #-}
1062{-# RULES
1063"TEXT takeWhile -> fused" [~1] forall p t.
1064 takeWhile p t = unstream (S.takeWhile p (stream t))
1065"TEXT takeWhile -> unfused" [1] forall p t.
1066 unstream (S.takeWhile p (stream t)) = takeWhile p t
1067 #-}
1069-- | /O(n)/ 'dropWhile' @p@ @t@ returns the suffix remaining after
1070-- 'takeWhile' @p@ @t@. Subject to fusion.
1071dropWhile :: (Char -> Bool) -> Text -> Text
1072dropWhile p t@(Text arr off len) = loop 0 0
1073 where loop !i !l | l >= len = empty
1074 | p c = loop (i+d) (l+d)
1075 | otherwise = Text arr (off+i) (len-l)
1076 where Iter c d = iter t i
1077{-# INLINE [1] dropWhile #-}
1079{-# RULES
1080"TEXT dropWhile -> fused" [~1] forall p t.
1081 dropWhile p t = unstream (S.dropWhile p (stream t))
1082"TEXT dropWhile -> unfused" [1] forall p t.
1083 unstream (S.dropWhile p (stream t)) = dropWhile p t
1084 #-}
1086-- | /O(n)/ 'dropWhileEnd' @p@ @t@ returns the prefix remaining after
1087-- dropping characters that fail the predicate @p@ from the end of
1088-- @t@. Subject to fusion.
1089-- Examples:
1091-- > dropWhileEnd (=='.') "foo..." == "foo"
1092dropWhileEnd :: (Char -> Bool) -> Text -> Text
1093dropWhileEnd p t@(Text arr off len) = loop (len-1) len
1094 where loop !i !l | l <= 0 = empty
1095 | p c = loop (i+d) (l+d)
1096 | otherwise = Text arr off l
1097 where (c,d) = reverseIter t i
1098{-# INLINE [1] dropWhileEnd #-}
1100{-# RULES
1101"TEXT dropWhileEnd -> fused" [~1] forall p t.
1102 dropWhileEnd p t = S.reverse (S.dropWhile p (S.reverseStream t))
1103"TEXT dropWhileEnd -> unfused" [1] forall p t.
1104 S.reverse (S.dropWhile p (S.reverseStream t)) = dropWhileEnd p t
1105 #-}
1107-- | /O(n)/ 'dropAround' @p@ @t@ returns the substring remaining after
1108-- dropping characters that fail the predicate @p@ from both the
1109-- beginning and end of @t@. Subject to fusion.
1110dropAround :: (Char -> Bool) -> Text -> Text
1111dropAround p = dropWhile p . dropWhileEnd p
1112{-# INLINE [1] dropAround #-}
1114-- | /O(n)/ Remove leading white space from a string. Equivalent to:
1116-- > dropWhile isSpace
1117stripStart :: Text -> Text
1118stripStart = dropWhile isSpace
1119{-# INLINE [1] stripStart #-}
1121-- | /O(n)/ Remove trailing white space from a string. Equivalent to:
1123-- > dropWhileEnd isSpace
1124stripEnd :: Text -> Text
1125stripEnd = dropWhileEnd isSpace
1126{-# INLINE [1] stripEnd #-}
1128-- | /O(n)/ Remove leading and trailing white space from a string.
1129-- Equivalent to:
1131-- > dropAround isSpace
1132strip :: Text -> Text
1133strip = dropAround isSpace
1134{-# INLINE [1] strip #-}
1136-- | /O(n)/ 'splitAt' @n t@ returns a pair whose first element is a
1137-- prefix of @t@ of length @n@, and whose second is the remainder of
1138-- the string. It is equivalent to @('take' n t, 'drop' n t)@.
1139splitAt :: Int -> Text -> (Text, Text)
1140splitAt n t@(Text arr off len)
1141 | n <= 0 = (empty, t)
1142 | n >= len = (t, empty)
1143 | otherwise = (Text arr off k, Text arr (off+k) (len-k))
1144 where k = loop 0 0
1145 loop !i !cnt
1146 | i >= len || cnt >= n = i
1147 | otherwise = loop (i+d) (cnt+1)
1148 where d = iter_ t i
1149{-# INLINE splitAt #-}
1151-- | /O(n)/ 'span', applied to a predicate @p@ and text @t@, returns
1152-- a pair whose first element is the longest prefix (possibly empty)
1153-- of @t@ of elements that satisfy @p@, and whose second is the
1154-- remainder of the list.
1155span :: (Char -> Bool) -> Text -> (Text, Text)
1156span p t = case span_ p t of
1157 (# hd,tl #) -> (hd,tl)
1158{-# INLINE span #-}
1160-- | /O(n)/ 'break' is like 'span', but the prefix returned is
1161-- over elements that fail the predicate @p@.
1162break :: (Char -> Bool) -> Text -> (Text, Text)
1163break p = span (not . p)
1164{-# INLINE break #-}
1166-- | /O(n)/ Group characters in a string according to a predicate.
1167groupBy :: (Char -> Char -> Bool) -> Text -> [Text]
1168groupBy p = loop
1169 where
1170 loop t@(Text arr off len)
1171 | null t = []
1172 | otherwise = text arr off n : loop (text arr (off+n) (len-n))
1173 where Iter c d = iter t 0
1174 n = d + findAIndexOrEnd (not . p c) (Text arr (off+d) (len-d))
1176-- | Returns the /array/ index (in units of 'Word16') at which a
1177-- character may be found. This is /not/ the same as the logical
1178-- index returned by e.g. 'findIndex'.
1179findAIndexOrEnd :: (Char -> Bool) -> Text -> Int
1180findAIndexOrEnd q t@(Text _arr _off len) = go 0
1181 where go !i | i >= len || q c = i
1182 | otherwise = go (i+d)
1183 where Iter c d = iter t i
1185-- | /O(n)/ Group characters in a string by equality.
1186group :: Text -> [Text]
1187group = groupBy (==)
1189-- | /O(n)/ Return all initial segments of the given 'Text', shortest
1190-- first.
1191inits :: Text -> [Text]
1192inits t@(Text arr off len) = loop 0
1193 where loop i | i >= len = [t]
1194 | otherwise = Text arr off i : loop (i + iter_ t i)
1196-- | /O(n)/ Return all final segments of the given 'Text', longest
1197-- first.
1198tails :: Text -> [Text]
1199tails t | null t = [empty]
1200 | otherwise = t : tails (unsafeTail t)
1202-- $split
1204-- Splitting functions in this library do not perform character-wise
1205-- copies to create substrings; they just construct new 'Text's that
1206-- are slices of the original.
1208-- | /O(m+n)/ Break a 'Text' into pieces separated by the first
1209-- 'Text' argument, consuming the delimiter. An empty delimiter is
1210-- invalid, and will cause an error to be raised.
1212-- Examples:
1214-- > splitOn "\r\n" "a\r\nb\r\nd\r\ne" == ["a","b","d","e"]
1215-- > splitOn "aaa" "aaaXaaaXaaaXaaa" == ["","X","X","X",""]
1216-- > splitOn "x" "x" == ["",""]
1218-- and
1220-- > intercalate s . splitOn s == id
1221-- > splitOn (singleton c) == split (==c)
1223-- In (unlikely) bad cases, this function's time complexity degrades
1224-- towards /O(n*m)/.
1225splitOn :: Text -> Text -> [Text]
1226splitOn pat@(Text _ _ l) src@(Text arr off len)
1227 | l <= 0 = emptyError "splitOn"
1228 | isSingleton pat = split (== unsafeHead pat) src
1229 | otherwise = go 0 (indices pat src)
1230 where
1231 go !s (x:xs) = textP arr (s+off) (x-s) : go (x+l) xs
1232 go s _ = [textP arr (s+off) (len-s)]
1233{-# INLINE [1] splitOn #-}
1235{-# RULES
1236"TEXT splitOn/singleton -> split/==" [~1] forall c t.
1237 splitOn (singleton c) t = split (==c) t
1238 #-}
1240-- | /O(n)/ Splits a 'Text' into components delimited by separators,
1241-- where the predicate returns True for a separator element. The
1242-- resulting components do not contain the separators. Two adjacent
1243-- separators result in an empty component in the output. eg.
1245-- > split (=='a') "aabbaca" == ["","","bb","c",""]
1246-- > split (=='a') "" == [""]
1247split :: (Char -> Bool) -> Text -> [Text]
1248split _ t@(Text _off _arr 0) = [t]
1249split p t = loop t
1250 where loop s | null s' = [l]
1251 | otherwise = l : loop (unsafeTail s')
1252 where (# l, s' #) = span_ (not . p) s
1253{-# INLINE split #-}
1255-- | /O(n)/ Splits a 'Text' into components of length @k@. The last
1256-- element may be shorter than the other chunks, depending on the
1257-- length of the input. Examples:
1259-- > chunksOf 3 "foobarbaz" == ["foo","bar","baz"]
1260-- > chunksOf 4 "haskell.org" == ["hask","ell.","org"]
1261chunksOf :: Int -> Text -> [Text]
1262chunksOf k = go
1263 where
1264 go t = case splitAt k t of
1265 (a,b) | null a -> []
1266 | otherwise -> a : go b
1267{-# INLINE chunksOf #-}
1269-- ----------------------------------------------------------------------------
1270-- * Searching
1272-------------------------------------------------------------------------------
1273-- ** Searching with a predicate
1275-- | /O(n)/ The 'find' function takes a predicate and a 'Text', and
1276-- returns the first element matching the predicate, or 'Nothing' if
1277-- there is no such element.
1278find :: (Char -> Bool) -> Text -> Maybe Char
1279find p t = S.findBy p (stream t)
1280{-# INLINE find #-}
1282-- | /O(n)/ The 'partition' function takes a predicate and a 'Text',
1283-- and returns the pair of 'Text's with elements which do and do not
1284-- satisfy the predicate, respectively; i.e.
1286-- > partition p t == (filter p t, filter (not . p) t)
1287partition :: (Char -> Bool) -> Text -> (Text, Text)
1288partition p t = (filter p t, filter (not . p) t)
1289{-# INLINE partition #-}
1291-- | /O(n)/ 'filter', applied to a predicate and a 'Text',
1292-- returns a 'Text' containing those characters that satisfy the
1293-- predicate.
1294filter :: (Char -> Bool) -> Text -> Text
1295filter p t = unstream (S.filter p (stream t))
1296{-# INLINE filter #-}
1298-- | /O(n+m)/ Find the first instance of @needle@ (which must be
1299-- non-'null') in @haystack@. The first element of the returned tuple
1300-- is the prefix of @haystack@ before @needle@ is matched. The second
1301-- is the remainder of @haystack@, starting with the match.
1303-- Examples:
1305-- > breakOn "::" "a::b::c" ==> ("a", "::b::c")
1306-- > breakOn "/" "foobar" ==> ("foobar", "")
1308-- Laws:
1310-- > append prefix match == haystack
1311-- > where (prefix, match) = breakOn needle haystack
1313-- If you need to break a string by a substring repeatedly (e.g. you
1314-- want to break on every instance of a substring), use 'breakOnAll'
1315-- instead, as it has lower startup overhead.
1317-- In (unlikely) bad cases, this function's time complexity degrades
1318-- towards /O(n*m)/.
1319breakOn :: Text -> Text -> (Text, Text)
1320breakOn pat src@(Text arr off len)
1321 | null pat = emptyError "breakOn"
1322 | otherwise = case indices pat src of
1323 [] -> (src, empty)
1324 (x:_) -> (textP arr off x, textP arr (off+x) (len-x))
1325{-# INLINE breakOn #-}
1327-- | /O(n+m)/ Similar to 'breakOn', but searches from the end of the
1328-- string.
1330-- The first element of the returned tuple is the prefix of @haystack@
1331-- up to and including the last match of @needle@. The second is the
1332-- remainder of @haystack@, following the match.
1334-- > breakOnEnd "::" "a::b::c" ==> ("a::b::", "c")
1335breakOnEnd :: Text -> Text -> (Text, Text)
1336breakOnEnd pat src = (reverse b, reverse a)
1337 where (a,b) = breakOn (reverse pat) (reverse src)
1338{-# INLINE breakOnEnd #-}
1340-- | /O(n+m)/ Find all non-overlapping instances of @needle@ in
1341-- @haystack@. Each element of the returned list consists of a pair:
1343-- * The entire string prior to the /k/th match (i.e. the prefix)
1345-- * The /k/th match, followed by the remainder of the string
1347-- Examples:
1349-- > breakOnAll "::" ""
1350-- > ==> []
1351-- > breakOnAll "/" "a/b/c/"
1352-- > ==> [("a", "/b/c/"), ("a/b", "/c/"), ("a/b/c", "/")]
1354-- In (unlikely) bad cases, this function's time complexity degrades
1355-- towards /O(n*m)/.
1357-- The @needle@ parameter may not be empty.
1358breakOnAll :: Text -- ^ @needle@ to search for
1359 -> Text -- ^ @haystack@ in which to search
1360 -> [(Text, Text)]
1361breakOnAll pat src@(Text arr off slen)
1362 | null pat = emptyError "breakOnAll"
1363 | otherwise = L.map step (indices pat src)
1364 where
1365 step x = (chunk 0 x, chunk x (slen-x))
1366 chunk !n !l = textP arr (n+off) l
1367{-# INLINE breakOnAll #-}
1369-------------------------------------------------------------------------------
1370-- ** Indexing 'Text's
1372-- $index
1374-- If you think of a 'Text' value as an array of 'Char' values (which
1375-- it is not), you run the risk of writing inefficient code.
1377-- An idiom that is common in some languages is to find the numeric
1378-- offset of a character or substring, then use that number to split
1379-- or trim the searched string. With a 'Text' value, this approach
1380-- would require two /O(n)/ operations: one to perform the search, and
1381-- one to operate from wherever the search ended.
1383-- For example, suppose you have a string that you want to split on
1384-- the substring @\"::\"@, such as @\"foo::bar::quux\"@. Instead of
1385-- searching for the index of @\"::\"@ and taking the substrings
1386-- before and after that index, you would instead use @breakOnAll \"::\"@.
1388-- | /O(n)/ 'Text' index (subscript) operator, starting from 0.
1389index :: Text -> Int -> Char
1390index t n = S.index (stream t) n
1391{-# INLINE index #-}
1393-- | /O(n)/ The 'findIndex' function takes a predicate and a 'Text'
1394-- and returns the index of the first element in the 'Text' satisfying
1395-- the predicate. Subject to fusion.
1396findIndex :: (Char -> Bool) -> Text -> Maybe Int
1397findIndex p t = S.findIndex p (stream t)
1398{-# INLINE findIndex #-}
1400-- | /O(n+m)/ The 'count' function returns the number of times the
1401-- query string appears in the given 'Text'. An empty query string is
1402-- invalid, and will cause an error to be raised.
1404-- In (unlikely) bad cases, this function's time complexity degrades
1405-- towards /O(n*m)/.
1406count :: Text -> Text -> Int
1407count pat src
1408 | null pat = emptyError "count"
1409 | isSingleton pat = countChar (unsafeHead pat) src
1410 | otherwise = L.length (indices pat src)
1411{-# INLINE [1] count #-}
1413{-# RULES
1414"TEXT count/singleton -> countChar" [~1] forall c t.
1415 count (singleton c) t = countChar c t
1416 #-}
1418-- | /O(n)/ The 'countChar' function returns the number of times the
1419-- query element appears in the given 'Text'. Subject to fusion.
1420countChar :: Char -> Text -> Int
1421countChar c t = S.countChar c (stream t)
1422{-# INLINE countChar #-}
1424-------------------------------------------------------------------------------
1425-- * Zipping
1427-- | /O(n)/ 'zip' takes two 'Text's and returns a list of
1428-- corresponding pairs of bytes. If one input 'Text' is short,
1429-- excess elements of the longer 'Text' are discarded. This is
1430-- equivalent to a pair of 'unpack' operations.
1431zip :: Text -> Text -> [(Char,Char)]
1432zip a b = S.unstreamList $ S.zipWith (,) (stream a) (stream b)
1433{-# INLINE [0] zip #-}
1435-- | /O(n)/ 'zipWith' generalises 'zip' by zipping with the function
1436-- given as the first argument, instead of a tupling function.
1437-- Performs replacement on invalid scalar values.
1438zipWith :: (Char -> Char -> Char) -> Text -> Text -> Text
1439zipWith f t1 t2 = unstream (S.zipWith g (stream t1) (stream t2))
1440 where g a b = safe (f a b)
1441{-# INLINE [0] zipWith #-}
1443-- | /O(n)/ Breaks a 'Text' up into a list of words, delimited by 'Char's
1444-- representing white space.
1445words :: Text -> [Text]
1446words t@(Text arr off len) = loop 0 0
1447 where
1448 loop !start !n
1449 | n >= len = if start == n
1450 then []
1451 else [Text arr (start+off) (n-start)]
1452 | isSpace c =
1453 if start == n
1454 then loop (start+1) (start+1)
1455 else Text arr (start+off) (n-start) : loop (n+d) (n+d)
1456 | otherwise = loop start (n+d)
1457 where Iter c d = iter t n
1458{-# INLINE words #-}
1460-- | /O(n)/ Breaks a 'Text' up into a list of 'Text's at
1461-- newline 'Char's. The resulting strings do not contain newlines.
1462lines :: Text -> [Text]
1463lines ps | null ps = []
1464 | otherwise = h : if null t
1465 then []
1466 else lines (unsafeTail t)
1467 where (# h,t #) = span_ (/= '\n') ps
1468{-# INLINE lines #-}
1471-- | /O(n)/ Portably breaks a 'Text' up into a list of 'Text's at line
1472-- boundaries.
1474-- A line boundary is considered to be either a line feed, a carriage
1475-- return immediately followed by a line feed, or a carriage return.
1476-- This accounts for both Unix and Windows line ending conventions,
1477-- and for the old convention used on Mac OS 9 and earlier.
1478lines' :: Text -> [Text]
1479lines' ps | null ps = []
1480 | otherwise = h : case uncons t of
1481 Nothing -> []
1482 Just (c,t')
1483 | c == '\n' -> lines t'
1484 | c == '\r' -> case uncons t' of
1485 Just ('\n',t'') -> lines t''
1486 _ -> lines t'
1487 where (h,t) = span notEOL ps
1488 notEOL c = c /= '\n' && c /= '\r'
1489{-# INLINE lines' #-}
1492-- | /O(n)/ Joins lines, after appending a terminating newline to
1493-- each.
1494unlines :: [Text] -> Text
1495unlines = concat . L.map (`snoc` '\n')
1496{-# INLINE unlines #-}
1498-- | /O(n)/ Joins words using single space characters.
1499unwords :: [Text] -> Text
1500unwords = intercalate (singleton ' ')
1501{-# INLINE unwords #-}
1503-- | /O(n)/ The 'isPrefixOf' function takes two 'Text's and returns
1504-- 'True' iff the first is a prefix of the second. Subject to fusion.
1505isPrefixOf :: Text -> Text -> Bool
1506isPrefixOf a@(Text _ _ alen) b@(Text _ _ blen) =
1507 alen <= blen && S.isPrefixOf (stream a) (stream b)
1508{-# INLINE [1] isPrefixOf #-}
1510{-# RULES
1511"TEXT isPrefixOf -> fused" [~1] forall s t.
1512 isPrefixOf s t = S.isPrefixOf (stream s) (stream t)
1513 #-}
1515-- | /O(n)/ The 'isSuffixOf' function takes two 'Text's and returns
1516-- 'True' iff the first is a suffix of the second.
1517isSuffixOf :: Text -> Text -> Bool
1518isSuffixOf a@(Text _aarr _aoff alen) b@(Text barr boff blen) =
1519 d >= 0 && a == b'
1520 where d = blen - alen
1521 b' | d == 0 = b
1522 | otherwise = Text barr (boff+d) alen
1523{-# INLINE isSuffixOf #-}
1525-- | /O(n+m)/ The 'isInfixOf' function takes two 'Text's and returns
1526-- 'True' iff the first is contained, wholly and intact, anywhere
1527-- within the second.
1529-- In (unlikely) bad cases, this function's time complexity degrades
1530-- towards /O(n*m)/.
1531isInfixOf :: Text -> Text -> Bool
1532isInfixOf needle haystack
1533 | null needle = True
1534 | isSingleton needle = S.elem (unsafeHead needle) . S.stream $ haystack
1535 | otherwise = not . L.null . indices needle $ haystack
1536{-# INLINE [1] isInfixOf #-}
1538{-# RULES
1539"TEXT isInfixOf/singleton -> S.elem/S.stream" [~1] forall n h.
1540 isInfixOf (singleton n) h = S.elem n (S.stream h)
1541 #-}
1543-------------------------------------------------------------------------------
1544-- * View patterns
1546-- | /O(n)/ Return the suffix of the second string if its prefix
1547-- matches the entire first string.
1549-- Examples:
1551-- > stripPrefix "foo" "foobar" == Just "bar"
1552-- > stripPrefix "" "baz" == Just "baz"
1553-- > stripPrefix "foo" "quux" == Nothing
1555-- This is particularly useful with the @ViewPatterns@ extension to
1556-- GHC, as follows:
1558-- > {-# LANGUAGE ViewPatterns #-}
1559-- > import Data.Text as T
1560-- >
1561-- > fnordLength :: Text -> Int
1562-- > fnordLength (stripPrefix "fnord" -> Just suf) = T.length suf
1563-- > fnordLength _ = -1
1564stripPrefix :: Text -> Text -> Maybe Text
1565stripPrefix p@(Text _arr _off plen) t@(Text arr off len)
1566 | p `isPrefixOf` t = Just $! textP arr (off+plen) (len-plen)
1567 | otherwise = Nothing
1569-- | /O(n)/ Find the longest non-empty common prefix of two strings
1570-- and return it, along with the suffixes of each string at which they
1571-- no longer match.
1573-- If the strings do not have a common prefix or either one is empty,
1574-- this function returns 'Nothing'.
1576-- Examples:
1578-- > commonPrefixes "foobar" "fooquux" == Just ("foo","bar","quux")
1579-- > commonPrefixes "veeble" "fetzer" == Nothing
1580-- > commonPrefixes "" "baz" == Nothing
1581commonPrefixes :: Text -> Text -> Maybe (Text,Text,Text)
1582commonPrefixes t0@(Text arr0 off0 len0) t1@(Text arr1 off1 len1) = go 0 0
1583 where
1584 go !i !j | i < len0 && j < len1 && a == b = go (i+d0) (j+d1)
1585 | i > 0 = Just (Text arr0 off0 i,
1586 textP arr0 (off0+i) (len0-i),
1587 textP arr1 (off1+j) (len1-j))
1588 | otherwise = Nothing
1589 where Iter a d0 = iter t0 i
1590 Iter b d1 = iter t1 j
1592-- | /O(n)/ Return the prefix of the second string if its suffix
1593-- matches the entire first string.
1595-- Examples:
1597-- > stripSuffix "bar" "foobar" == Just "foo"
1598-- > stripSuffix "" "baz" == Just "baz"
1599-- > stripSuffix "foo" "quux" == Nothing
1601-- This is particularly useful with the @ViewPatterns@ extension to
1602-- GHC, as follows:
1604-- > {-# LANGUAGE ViewPatterns #-}
1605-- > import Data.Text as T
1606-- >
1607-- > quuxLength :: Text -> Int
1608-- > quuxLength (stripSuffix "quux" -> Just pre) = T.length pre
1609-- > quuxLength _ = -1
1610stripSuffix :: Text -> Text -> Maybe Text
1611stripSuffix p@(Text _arr _off plen) t@(Text arr off len)
1612 | p `isSuffixOf` t = Just $! textP arr off (len-plen)
1613 | otherwise = Nothing
1615-- | Add a list of non-negative numbers. Errors out on overflow.
1616sumP :: String -> [Int] -> Int
1617sumP fun = go 0
1618 where go !a (x:xs)
1619 | ax >= 0 = go ax xs
1620 | otherwise = overflowError fun
1621 where ax = a + x
1622 go a _ = a
1624emptyError :: String -> a
1625emptyError fun = P.error $ "Data.Text." ++ fun ++ ": empty input"
1627overflowError :: String -> a
1628overflowError fun = P.error $ "Data.Text." ++ fun ++ ": size overflow"
1630-- | /O(n)/ Make a distinct copy of the given string, sharing no
1631-- storage with the original string.
1633-- As an example, suppose you read a large string, of which you need
1634-- only a small portion. If you do not use 'copy', the entire original
1635-- array will be kept alive in memory by the smaller string. Making a
1636-- copy \"breaks the link\" to the original array, allowing it to be
1637-- garbage collected if there are no other live references to it.
1638copy :: Text -> Text
1639copy (Text arr off len) = Text (A.run go) 0 len
1640 where
1641 go = do
1642 marr <- A.new len
1643 A.copyI marr 0 arr off len
1644 return marr