Created
January 12, 2022 16:04
-
-
Save SamirTalwar/60399b7f869b1838a1e43959e7a2c332 to your computer and use it in GitHub Desktop.
An example of data families, in preparation for an article.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| {-# LANGUAGE NoStarIsType #-} | |
| {-# LANGUAGE TypeFamilies #-} | |
| import Data.Kind (Type) | |
| import Prelude hiding (sum) | |
| class CanSum a where | |
| data Sum a | |
| buildSum :: a -> Sum a | |
| runSum :: Num n => Sum a -> n | |
| sum :: (CanSum a, Num n) => a -> n | |
| sum = runSum . buildSum | |
| instance CanSum Int where | |
| data Sum Int = SumInt Int | |
| buildSum = SumInt | |
| runSum (SumInt x) = fromIntegral x | |
| instance CanSum Integer where | |
| data Sum Integer = SumInteger Integer | |
| buildSum = SumInteger | |
| runSum (SumInteger x) = fromIntegral x | |
| instance (CanSum a, CanSum b) => CanSum (a, b) where | |
| data Sum (a, b) = SumPair (Sum a) (Sum b) | |
| buildSum (x, y) = SumPair (buildSum x) (buildSum y) | |
| runSum (SumPair x y) = runSum x + runSum y | |
| instance (CanSum a) => CanSum [a] where | |
| data Sum [a] = SumList [Sum a] | |
| buildSum xs = SumList (map buildSum xs) | |
| runSum (SumList xs) = foldr (+) 0 $ map runSum xs | |
| {- | |
| sum ((1, 2), ([3, 4, 5], [(6, 7), (8, 9)])) | |
| --> 45 | |
| -} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment