Skip to content

Functors for the "Generic Extensions to Type Operators" #3

@CMCDragonkai

Description

@CMCDragonkai

I sometimes find it easier to understand if I relate the PFPL to equivalent constructs in Haskell.

Regarding today's meeting for page 123. We have a 5 polynomial type operators. Here are some equivalences I've found:

For 14.3.a:

map{t.t}(x.e')(e) -> [e/x]e'
> import Data.Functor.Identity
> instance (Show a) => Show (Identity a) where
> |     show (Identity a) = "Identity " ++ show a
> |
> fmap (\x -> x + 1) (Identity 3)
Identity 4
> :info Identity
newtype Identity a = Identity {runIdentity :: a}
        -- Defined in ‘Data.Functor.Identity’
instance Show a => Show (Identity a)
  -- Defined at <interactive>:24:10
instance Monad Identity -- Defined in ‘Data.Functor.Identity’
instance Functor Identity -- Defined in ‘Data.Functor.Identity’

For 14.3b:

map{t.unit}(x.e')(e) -> e
> import Data.Proxy
> fmap (\x -> x) Proxy
Proxy
it :: Proxy b
> :info Proxy
type role Proxy phantom
data Proxy (t :: k) = Proxy
        -- Defined in ‘Data.Proxy’
instance Bounded (Proxy s) -- Defined in ‘Data.Proxy’
instance Enum (Proxy s) -- Defined in ‘Data.Proxy’
instance Eq (Proxy s) -- Defined in ‘Data.Proxy’
instance Monad Proxy -- Defined in ‘Data.Proxy’
instance Functor Proxy -- Defined in ‘Data.Proxy’
instance Ord (Proxy s) -- Defined in ‘Data.Proxy’
instance Read (Proxy s) -- Defined in ‘Data.Proxy’
instance Show (Proxy s) -- Defined in ‘Data.Proxy’

There used to be a Data.Unit in category-extras package, but it was removed.

For 14.3c:

map{t.tau1 * tau2}(x.e')(e) -> <map{t.tau1}(x.e')(e.l),map{t.tau2}(x.e')(e.r)>

Unknown. Originally I thought it was a tuple. But it isn't. Also this is close data Pair a = Pair a a but it doesn't exactly match {t.tau1 * tau2}, it would be more like {t.t * t}.

For 14.3d:

map{t.void}(x.e')(e) -> abort(e)

Could be Data.Void, but it's not an instance of the Functor type class. Also I couldn't make it an instance of Functor because the kind is * and Functor needs a kind of * -> *.

> import Data.Void
> instance Functor Void where
> |     fmap _ v = absurd v
> |
    The first argument of ‘Functor’ should have kind ‘* -> *’,
      but ‘Void’ has kind ‘*’
    In the instance declaration for ‘Functor Void’

The closest thing to the same behaviour is...

> fmap (\x -> x) undefined
*** Exception: Prelude.undefined

For 14.3e:

map{t.tau1 + tau2}(x.e')(e) -> case e { l.x1 -> l.map{t.tau1}(x.e')(x1) | r.x2 -> r.map{t.tau2}(x.e')(x2) }

Not sure, could it be the Either functor?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions