Skip to content
This repository has been archived by the owner on Dec 5, 2019. It is now read-only.

Commit

Permalink
Added metamacro_take(), to return the prefix of an argument list
Browse files Browse the repository at this point in the history
  • Loading branch information
jspahrsummers committed Jun 20, 2012
1 parent dc43cb3 commit f7c3bee
Show file tree
Hide file tree
Showing 2 changed files with 38 additions and 0 deletions.
30 changes: 30 additions & 0 deletions include/metamacros.h
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,13 @@
#define metamacro_tail(...) \
metamacro_tail_(__VA_ARGS__)

/**
* Returns the first N (up to twenty) variadic arguments as a new argument list.
* At least N variadic arguments must be provided.
*/
#define metamacro_take(N, ...) \
metamacro_concat(metamacro_take, N)(__VA_ARGS__)

/**
* Decrements VAL, which must be a number between one and twenty, inclusive.
*
Expand Down Expand Up @@ -641,4 +648,27 @@ metamacro_if_eq(0, 1)(true)(false)
#define metamacro_if_eq_recursive19(VALUE) metamacro_if_eq_recursive18(metamacro_dec(VALUE))
#define metamacro_if_eq_recursive20(VALUE) metamacro_if_eq_recursive19(metamacro_dec(VALUE))

// metamacro_take expansions
#define metamacro_take0(...)
#define metamacro_take1(...) metamacro_head(__VA_ARGS__)
#define metamacro_take2(...) metamacro_head(__VA_ARGS__), metamacro_take1(metamacro_tail(__VA_ARGS__))
#define metamacro_take3(...) metamacro_head(__VA_ARGS__), metamacro_take2(metamacro_tail(__VA_ARGS__))
#define metamacro_take4(...) metamacro_head(__VA_ARGS__), metamacro_take3(metamacro_tail(__VA_ARGS__))
#define metamacro_take5(...) metamacro_head(__VA_ARGS__), metamacro_take4(metamacro_tail(__VA_ARGS__))
#define metamacro_take6(...) metamacro_head(__VA_ARGS__), metamacro_take5(metamacro_tail(__VA_ARGS__))
#define metamacro_take7(...) metamacro_head(__VA_ARGS__), metamacro_take6(metamacro_tail(__VA_ARGS__))
#define metamacro_take8(...) metamacro_head(__VA_ARGS__), metamacro_take7(metamacro_tail(__VA_ARGS__))
#define metamacro_take9(...) metamacro_head(__VA_ARGS__), metamacro_take8(metamacro_tail(__VA_ARGS__))
#define metamacro_take10(...) metamacro_head(__VA_ARGS__), metamacro_take9(metamacro_tail(__VA_ARGS__))
#define metamacro_take11(...) metamacro_head(__VA_ARGS__), metamacro_take10(metamacro_tail(__VA_ARGS__))
#define metamacro_take12(...) metamacro_head(__VA_ARGS__), metamacro_take11(metamacro_tail(__VA_ARGS__))
#define metamacro_take13(...) metamacro_head(__VA_ARGS__), metamacro_take12(metamacro_tail(__VA_ARGS__))
#define metamacro_take14(...) metamacro_head(__VA_ARGS__), metamacro_take13(metamacro_tail(__VA_ARGS__))
#define metamacro_take15(...) metamacro_head(__VA_ARGS__), metamacro_take14(metamacro_tail(__VA_ARGS__))
#define metamacro_take16(...) metamacro_head(__VA_ARGS__), metamacro_take15(metamacro_tail(__VA_ARGS__))
#define metamacro_take17(...) metamacro_head(__VA_ARGS__), metamacro_take16(metamacro_tail(__VA_ARGS__))
#define metamacro_take18(...) metamacro_head(__VA_ARGS__), metamacro_take17(metamacro_tail(__VA_ARGS__))
#define metamacro_take19(...) metamacro_head(__VA_ARGS__), metamacro_take18(metamacro_tail(__VA_ARGS__))
#define metamacro_take20(...) metamacro_head(__VA_ARGS__), metamacro_take19(metamacro_tail(__VA_ARGS__))

#endif
8 changes: 8 additions & 0 deletions tests/metamacros_test.c
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@
#define test_recursive_foreach(INDEX, VALUE) \
metamacro_foreach_cxt_recursive(test_stringify_cxt,, "foo", (INDEX, VALUE))

#define simple_concat(INDEX, STR) \
STR

void metamacros_test (void) {
assert(metamacro_at(0, -15) == -15);
assert(metamacro_at(20, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -15) == -15);
Expand Down Expand Up @@ -112,4 +115,9 @@ void metamacros_test (void) {
assert(0 == strcmp(metamacro_if_eq(0, 0)("A")(metamacro_if_eq_recursive(1, 1)("B")("C")), "A"));
assert(0 == strcmp(metamacro_if_eq(0, 1)("A")(metamacro_if_eq_recursive(1, 1)("B")("C")), "B"));
assert(0 == strcmp(metamacro_if_eq(0, 1)("A")(metamacro_if_eq_recursive(0, 1)("B")("C")), "C"));

assert(0 == strcmp(metamacro_foreach(simple_concat,, metamacro_take(1, "foo", "bar", "buzz")), "foo"));
assert(0 == strcmp(metamacro_foreach(simple_concat,, metamacro_take(3, "foo", "bar", "buzz")), "foobarbuzz"));
assert(0 == strcmp(metamacro_foreach(test_stringify,, metamacro_take(20, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19)),
"001122334455667788991010111112121313141415151616171718181919"));
}

0 comments on commit f7c3bee

Please sign in to comment.