Skip to content

lack of improvement/reduction with TFs

{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE FunctionalDependencies #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE TypeFamilies #-}
data A = A
data B = B

class C a where c :: a -> String
instance C Bool where c _ = "Bool"
instance C Char where c _ = "Char"

-- via TFs
type family TF a
type instance TF A = Char
type instance TF B = Bool

tf :: forall a b. (b ~ TF a,C b) => a -> String
tf a = c (undefined:: b) 

-- via FDs
class FD a b | a -> b
instance FD A Char
instance FD B Bool

fd :: forall a b. (FD a b,C b) => a -> String
fd a = c (undefined:: b) 

for some reason, the TF version doesn't work as well as the FD version:

*Main> fd A
"Char"
*Main> fd B
"Bool"
*Main> tf A

<interactive>:1:0:
    No instance for (C (TF A))
      arising from a use of `tf' at <interactive>:1:0-3
    Possible fix: add an instance declaration for (C (TF A))
    In the expression: tf A
    In the definition of `it': it = tf A
*Main> :t undefined :: (b~TF A)=>b
undefined :: (b~TF A)=>b :: TF A
*Main> :t undefined :: (FD A b)=>b
undefined :: (FD A b)=>b :: Char

this is with GHCi, version 6.9.20080217.

the result of the TF is "known", even if not used:

*Main> :t undefined :: (b~TF A,b~Char)=>b
undefined :: (b~TF A,b~Char)=>b :: TF A
*Main> :t undefined :: (b~TF A,b~Bool)=>b

<interactive>:1:0:
    Couldn't match expected type `Bool' against inferred type `Char'
Trac metadata
Trac field Value
Version 6.9
Type Bug
TypeOfFailure OtherFailure
Priority normal
Resolution Unresolved
Component Compiler (Type checker)
Test case
Differential revisions
BlockedBy
Related
Blocking
CC
Operating system Unknown
Architecture Unknown
To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information