// 1. put a real object system inside the tree-based parsing stuff // 2. implement ? operator (zero or one of something) // 3. implement . leaf type (any valid character, NOT the end of the input) // 4. implement ! operator (prefix, inverts the subexpression) !"abc" matches not "abc" without moving input // 5. make a function to print the tree describing the pattern #include #include #include typedef union Object Object; typedef union Object *oop; enum type { Integer, String, }; struct Integer { enum type type; int i; }; struct String { enum type type; char *s; int len; }; union Object { enum type type; struct Integer Integer; struct String String; }; oop mkObject(size_t size, enum type type) { oop o= calloc(1, size); o->type = type; return o; } oop _checktype(oop object, enum type type) { if (object->type == type) return object; fprintf(stderr, "\naccesing type %i as if it were a %i\n", object->type, type); exit(1); return 0; } #define new(type) mkObject(sizeof(struct type), type) #define get(object, type, member) (_checktype(object, type)->type.member) oop mkInt(int i) { oop o= new(Integer); o->Integer.i = i; return o; } oop mkStr(char *s) { oop o= new(String); o->String.s = s; o->String.len = strlen(s); return o; } void println(oop o) { switch (o->type) { case Integer: printf("%i\n", get(o, Integer, i)); return; case String: printf("%.*s\n", get(o, String, len), get(o, String, s)); return; } abort(); } int main(int argc, char **argv) { println(mkInt(42)); println(mkStr("hello world")); return 0; }