Name: Anonymous 2013-03-18 16:41
Anyone wanna come?
#include <stdlib.h>
#include <stdio.h>
#define VALUE(f,t, v) (t*)((f*)v)->current
#define CAST(t,v) ((t*)v)
#define GEN(t,v) ((t*)v)->current
/* Forgetful functor */
#define FORGET(t) t->object
typedef void * value;
/* Generic function :: a -> b */
typedef void * (*arr)(void *);
/* Generic fmap :: f a -> (a -> b) -> f b */
typedef void * (*fmap)(void *, arr);
/* Functors ala haskell */
typedef struct functor {
value object;
fmap arrow;
} functor;
typedef struct maybe {
int nothing;
value current;
} maybe;
/* maybe has two constructors */
maybe * nothing(){
maybe * nothing = malloc(sizeof(maybe));
nothing->nothing = 1;
nothing->current = NULL;
return nothing;
}
maybe * just(value item){
maybe * just = malloc(sizeof(maybe));
just->nothing = 0;
just->current = item;
return just;
}
/* functor invoker */
void * map(functor * f, arr g){
fmap h = f->arrow;
f->object = h(f->object, g);
return f;
}
/* Functor instance for maybe */
void * mFunctor(void * m, arr f){
if(CAST(maybe,m)->nothing){
return (void *) m;
} else {
CAST(maybe, m)->current = f(GEN(maybe,m));
return m;
}
}
functor * maybeFunctor (maybe * object){
functor * maybe = malloc(sizeof(functor));
maybe->object = object;
maybe->arrow = &mFunctor;
return maybe;
}
/* I actually need an garbage collector. This will be so much nicer */
int main(int argc, char *argv[]) {
int x = 1;
maybe * y = just(&x);
/* this is not needed but it gives an haskelly feel to the code */
functor * f = maybeFunctor(y);
void * _in(void *x){
int * y = CAST(int, x);
(*y)++;
return y;
};
functor * g = map(f, _in);
printf("%d", *VALUE(maybe, int, FORGET(g)));
return 0;
}