Основные преимущества Backpack:
- Гарантированное отсутствие снижения производительности (использование классов типов может привести к снижению производительности из-за того, как они реализованы в Haskell).Это чрезвычайно важно при работе со строковыми типами данных, анализаторами, контейнерами и т. Д.
- Более чистый и приятный код по сравнению с использованием классов типов или семейств типов.
Я написал сообщение в блогеоб одном конкретном использовании Backpack: реализация полиморфного интерфейса для структур данных контейнеров:
Имея такойИнтерфейс для контейнеров позволяет:
- Писать полиморфные функции, которые работают с любым контейнером (например,
Map
, HashMap
и IntMap
). - Написать один набор тестов длясвойства контейнеров и использовать его в каждом пакете без дублирования кода.
- Написать единый тест и использовать с каждой структурой данных контейнеров без снижения производительности.
Если условия сделать код чище.Это подпись функции groupBy
, реализованной с помощью Backpack:
groupBy :: forall k f a . (Foldable f, Key k) => (a -> k) -> f a -> Map k (NonEmpty a)
Понятно, и это просто обычный Haskell.Если вы реализуете интерфейс для контейнеров, использующих классы типов и семейства типов (это сделано в relude
, эта подпись будет выглядеть так:
groupBy
:: forall f t a . (Foldable f, DynamicMap t, Val t ~ NonEmpty a, Monoid t)
=> (a -> Key t) -> f a -> t
Гораздо сложнее читать и понимать.
Также недавно обсуждалось , что Backpack может помочь избежать CPP, когда вам нужно скомпилировать код на Haskell для разных платформ (он же условная компиляция).