11-- | Parallel versions of 'filter' and 'simpleFilter'
22
33module Text.Fuzzy.Parallel
4- ( filter , filter',
4+ ( filter , filter', matchPar,
55 simpleFilter, simpleFilter',
66 match, defChunkSize, defMaxResults,
7- Scored (.. )
7+ Scored (.. ), Matcher ( .. )
88) where
99
1010import Control.Parallel.Strategies (evalList , parList , rseq , using )
@@ -18,6 +18,8 @@ import Prelude hiding (filter)
1818data Scored a = Scored { score :: ! Int , original :: ! a }
1919 deriving (Functor , Show )
2020
21+ newtype Matcher a = Matcher { runMatcher :: T. Text -> [T. Text ] -> [Scored a ] }
22+
2123-- | Returns the rendered output and the
2224-- matching score for a pattern and a text.
2325-- Two examples are given below:
@@ -103,15 +105,29 @@ filter' :: Int -- ^ Chunk size. 1000 works well.
103105 -- ^ Custom scoring function to use for calculating how close words are
104106 -- When the function returns Nothing, this means the values are incomparable.
105107 -> [Scored t ] -- ^ The list of results, sorted, highest score first.
106- filter' chunkSize maxRes pat ts extract match' = partialSortByAscScore maxRes perfectScore (concat vss)
108+ filter' chunkSize maxRes pat ts extract match' = partialSortByAscScore maxRes perfectScore $
109+ matchPar chunkSize pat' ts extract match'
107110 where
108- -- Preserve case for the first character, make all others lowercase
109- pat' = case T. uncons pat of
111+ perfectScore = fromMaybe (error $ T. unpack pat) $ match' pat pat
112+ -- Preserve case for the first character, make all others lowercase
113+ pat' = case T. uncons pat of
110114 Just (c, rest) -> T. cons c (T. toLower rest)
111115 _ -> pat
112- vss = map (mapMaybe (\ t -> flip Scored t <$> match' pat' (extract t))) (chunkList chunkSize ts)
116+
117+ matchPar
118+ :: Int -- ^ Chunk size. 1000 works well.
119+ -> T. Text -- ^ Pattern.
120+ -> [t ] -- ^ The list of values containing the text to search in.
121+ -> (t -> T. Text ) -- ^ The function to extract the text from the container.
122+ -> (T. Text -> T. Text -> Maybe Int )
123+ -- ^ Custom scoring function to use for calculating how close words are
124+ -- When the function returns Nothing, this means the values are incomparable.
125+ -> [Scored t ] -- ^ The list of results, sorted, highest score first.
126+ {-# INLINABLE matchPar #-}
127+ matchPar chunkSize pat ts extract match' = concat vss
128+ where
129+ vss = map (mapMaybe (\ t -> flip Scored t <$> match' pat (extract t))) (chunkList chunkSize ts)
113130 `using` parList (evalList rseq)
114- perfectScore = fromMaybe (error $ T. unpack pat) $ match' pat' pat'
115131
116132-- | The function to filter a list of values by fuzzy search on the text extracted from them,
117133-- using a custom matching function which determines how close words are.
0 commit comments