我正在编写一个函数,用于在任意符号序列中进行搜索。我希望使其足够通用,可以在列表、Foldable以及ByteString和Text上运行。将其泛化到Foldable很简单。但如何包括ByteString和Text呢?当然,我可以将ByteString转换为列表,然后调用我的函数,但我会失去所有ByteString的优势。
让我们举一个具体的例子,假设我们想要制作一个直方图函数:
让我们举一个具体的例子,假设我们想要制作一个直方图函数:
import Control.Monad.State
import qualified Data.Foldable as F
import Data.Map.Strict (Map)
import qualified Data.Map.Strict as Map
import Data.Word
import qualified Data.ByteString as B
import qualified Data.Text as T
type Histogram a = Map a Int
empty :: (Ord a) => Histogram a
empty = Map.empty
histogramStep :: (Ord a) => a -> Histogram a -> Histogram a
histogramStep k = Map.insertWith (+) k 1
histogram :: (Ord a, F.Foldable t) => t a -> Histogram a
histogram = F.foldl (flip histogramStep) empty
但是既然ByteString
和
histogramBS :: B.ByteString -> Histogram Word8
histogramBS = B.foldl (flip histogramStep) empty
histogramText :: T.Text -> Histogram Char
histogramText = T.foldl (flip histogramStep) empty
在像Haskell这样的函数式语言中,人们不会期望出现这种情况。
如何使其通用化,一次编写histogram
并永久使用?