Skip to content

Instantly share code, notes, and snippets.

@dmbfm
Last active December 7, 2020 03:02
Show Gist options
  • Save dmbfm/d23971146837ed27e9900562a42089a8 to your computer and use it in GitHub Desktop.
Save dmbfm/d23971146837ed27e9900562a42089a8 to your computer and use it in GitHub Desktop.
Playing around with the idea of Maybe/Option/Optional type in C using silly macros
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#define maybe(type) maybe_##type
#define some(type, v) ((maybe(type)) { .is_something = 1, .value = v})
#define nothing(type) ((maybe(type)) { .is_something = 0 })
#define unwrap(x) (is_nothing(x) ? abort() : 0, x.value)
#define is_nothing(x) (x.is_something == 0)
#define ifsome(x) if (!is_nothing(x))
#define maybe_set(x,v) (x.value=v)
#define make_maybe_type(type) \
typedef struct\
{\
u8 is_something;\
type value;\
} maybe(type);
typedef int* intptr;
typedef uint8_t u8;
typedef void* voidptr;
make_maybe_type(int);
make_maybe_type(intptr);
make_maybe_type(voidptr);
maybe(voidptr) alloc(size_t size) {
void *mem = malloc(size);
if (!mem) {
return nothing(voidptr);
}
return some(voidptr, mem);
}
typedef struct
{
maybe(int) initial_x;
maybe(int) initial_y;
} Config;
int main(void) {
maybe(int) x = some(int, 10);
maybe(intptr) z = some(intptr, &x.value);
if (is_nothing(x)) {
printf("Nothing!\n");
} else {
printf("Value = %d\n", x.value);
}
Config c = { 0 };
int xpos = is_nothing(c.initial_x) ? 100 : c.initial_x.value;
int ypos = is_nothing(c.initial_y) ? 100 : c.initial_y.value;
printf("(%d, %d)\n", xpos, ypos);
int *values = unwrap(alloc(100));
x = some(int, 234);
ifsome(x) {
printf("Value = %d\n", x.value);
}
return 0;
}
@dmbfm
Copy link
Author

dmbfm commented Dec 7, 2020

Could be useful for configuration/options and small programs/tools...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment