Skip to content

Instantly share code, notes, and snippets.

@tdietert
Last active June 16, 2019 21:18
Show Gist options
  • Save tdietert/60430966dfbc4c88a30487f267f5bdae to your computer and use it in GitHub Desktop.
Save tdietert/60430966dfbc4c88a30487f267f5bdae to your computer and use it in GitHub Desktop.
{-# LANGUAGE DataKinds #-}
{-# LANGUAGE KindSignatures #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE PolyKinds #-}
{-# LANGUAGE RankNTypes #-}
module Singletons where
import Data.Kind (Type)
-- import GHC.TypeNats
canMakeMove :: Int -> Int -> Either [Char] Bool
canMakeMove n m
| n == m = Left "Can't call function w/ equal args!"
| n > m = Right True
| n < m = Right False
-- foo :: 5
-- foo = undefined
foo2 :: (a :: Type)
foo2 = undefined
-- Singleton:
--
--
data Nat -- defines the "kind" Nat
= Zero -- defines the "type" Zero
| Succ Nat -- defines the "type" Succ Nat
data SNat (n :: Nat) where
SZero :: SNat 'Zero
SSucc :: SNat n -> SNat ('Succ n)
type family (:==:) (a :: k) (b :: k) where
x :==: x = 'True
x :==: y = 'False
f :: SNat 'Zero
f = SZero
instance Eq (SNat 'Zero) where
SZero /= SZero = False
instance Eq (SNat n) => Eq (SNat ('Succ n)) where
SSucc n /= SZero = True
SSucc n /= SSucc m = n /= m
sCanMakeMove :: ((n :==: m) ~ 'False) => SNat n -> SNat m -> Bool
sCanMakeMove n m = True
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment