summaryrefslogtreecommitdiff
path: root/transpose.h
blob: 02471fffc2a77beddd255f7b00bc1d9e4d12558e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
#define EMPTY()
#define EXPAND(...) __VA_ARGS__
#define DEFER(id) id EMPTY()
#define OBSTRUCT(...) __VA_ARGS__ DEFER(EMPTY)()
#define CAR(a, ...) a
#define CDR(a, ...) __VA_OPT__((__VA_ARGS__))

#define I_A() A
#define I_B() B
#define I_C() C

#ifndef DELIM
    #define DELIM COMMA
#endif
#ifndef P
    #define P(...) { __VA_ARGS__ } COMMA
#endif

#define COMMA ,
#define HAS(b, ...) __VA_OPT__(__VA_ARGS__ b)

#define EVAL(...)  EVAL1(EVAL1(EVAL1(__VA_ARGS__)))
#define EVAL1(...) EVAL2(EVAL2(EVAL2(__VA_ARGS__)))
#define EVAL2(...) EVAL3(EVAL3(EVAL3(__VA_ARGS__)))
#define EVAL3(...) EVAL4(EVAL4(EVAL4(__VA_ARGS__)))
#define EVAL4(...) EVAL5(EVAL5(EVAL5(__VA_ARGS__)))
#define EVAL5(...) EVAL6(EVAL6(EVAL6(__VA_ARGS__)))
#define EVAL6(...) EVAL7(EVAL7(EVAL7(__VA_ARGS__)))
#define EVAL7(...) __VA_ARGS__

// #define DEFER0(...) DEFER1(DEFER1(DEFER1(__VA_ARGS__)))
// #define DEFER1(...) DEFER2(DEFER2(DEFER2(__VA_ARGS__)))
// #define DEFER2(...) DEFER3(DEFER3(DEFER3(__VA_ARGS__)))
// #define DEFER3(...) DEFER4(DEFER4(DEFER4(__VA_ARGS__)))
// #define DEFER4(...) DEFER5(DEFER5(DEFER5(__VA_ARGS__)))
// #define DEFER5(...) DEFER6(DEFER6(DEFER6(__VA_ARGS__)))
// #define DEFER6(...) DEFER (DEFER (DEFER (__VA_ARGS__)))

#define A(a, ...) HAS(__VA_OPT__(DELIM OBSTRUCT(I_A)()(__VA_ARGS__)), CAR a)
#define B(a, ...) HAS(__VA_OPT__(COMMA OBSTRUCT(I_B)()(__VA_ARGS__)), CDR a)
#define C(...) __VA_OPT__(P(A(__VA_ARGS__)) DEFER(OBSTRUCT(I_C)())DEFER(EXPAND)((B(__VA_ARGS__))))

#define TRANSPOSE(...) EVAL(C(__VA_ARGS__))

// #define TEST
#ifdef TEST
    TRANSPOSE((1, 2, 3), (4, 5, 6))
    TRANSPOSE((1, 2, 3), (4, 5, 6), (4, 5, 6), (4, 5, 6), (4, 5, 6))
    // EXPAND(EXPAND(EXPAND(EXPAND(EXPAND(EXPAND(B((1, 4), (2, 6))))))))
#endif