macros.hh 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657
  1. // -*- mode: c++; coding: utf-8 -*-
  2. // ra-ra - Basic macros and types.
  3. // (c) Daniel Llorens - 2005--2023
  4. // This library is free software; you can redistribute it and/or modify it under
  5. // the terms of the GNU Lesser General Public License as published by the Free
  6. // Software Foundation; either version 3 of the License, or (at your option) any
  7. // later version.
  8. #pragma once
  9. #include <cstddef>
  10. #include <type_traits>
  11. #define STRINGIZE_( x ) #x
  12. #define STRINGIZE( x ) STRINGIZE_( x )
  13. #define JOIN_( x, y ) x##y
  14. #define JOIN( x, y ) JOIN_( x, y )
  15. // see http://stackoverflow.com/a/1872506
  16. #define FOR_EACH_1(what, x, ...) what(x)
  17. #define FOR_EACH_2(what, x, ...) what(x) FOR_EACH_1(what, __VA_ARGS__)
  18. #define FOR_EACH_3(what, x, ...) what(x) FOR_EACH_2(what, __VA_ARGS__)
  19. #define FOR_EACH_4(what, x, ...) what(x) FOR_EACH_3(what, __VA_ARGS__)
  20. #define FOR_EACH_5(what, x, ...) what(x) FOR_EACH_4(what, __VA_ARGS__)
  21. #define FOR_EACH_6(what, x, ...) what(x) FOR_EACH_5(what, __VA_ARGS__)
  22. #define FOR_EACH_7(what, x, ...) what(x) FOR_EACH_6(what, __VA_ARGS__)
  23. #define FOR_EACH_8(what, x, ...) what(x) FOR_EACH_7(what, __VA_ARGS__)
  24. #define FOR_EACH_9(what, x, ...) what(x) FOR_EACH_8(what, __VA_ARGS__)
  25. #define FOR_EACH_10(what, x, ...) what(x) FOR_EACH_9(what, __VA_ARGS__)
  26. #define FOR_EACH_11(what, x, ...) what(x) FOR_EACH_10(what, __VA_ARGS__)
  27. #define FOR_EACH_12(what, x, ...) what(x) FOR_EACH_11(what, __VA_ARGS__)
  28. #define FOR_EACH_NARG(...) FOR_EACH_NARG_(__VA_ARGS__, FOR_EACH_RSEQ_N())
  29. #define FOR_EACH_NARG_(...) FOR_EACH_ARG_N(__VA_ARGS__)
  30. #define FOR_EACH_ARG_N(_1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, N, ...) N
  31. #define FOR_EACH_RSEQ_N() 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0
  32. #define FOR_EACH_(N, what, ...) JOIN(FOR_EACH_, N)(what, __VA_ARGS__)
  33. #define FOR_EACH(what, ...) FOR_EACH_(FOR_EACH_NARG(__VA_ARGS__), what, __VA_ARGS__)
  34. #define RA_FWD(a) std::forward<decltype(a)>(a)
  35. // Assign ops for settable array iterators; these must be members. For containers & views this might be defined differently.
  36. // Forward to make sure value y is not misused as ref [ra5].
  37. #define RA_DEF_ASSIGNOPS_LINE(OP) \
  38. for_each([](auto && y, auto && x) { RA_FWD(y) OP x; }, *this, x)
  39. #define RA_DEF_ASSIGNOPS(OP) \
  40. template <class X> constexpr void operator OP(X && x) { RA_DEF_ASSIGNOPS_LINE(OP); }
  41. // But see local DEF_ASSIGNOPS elsewhere.
  42. #define RA_DEF_ASSIGNOPS_DEFAULT_SET \
  43. FOR_EACH(RA_DEF_ASSIGNOPS, =, *=, +=, -=, /=)
  44. // Restate RA_DEF_ASSIGNOPS for expression classes since the template doesn't replace the assignment ops.
  45. #define RA_DEF_ASSIGNOPS_SELF(TYPE) \
  46. TYPE & operator=(TYPE && x) { RA_DEF_ASSIGNOPS_LINE(=); return *this; } \
  47. TYPE & operator=(TYPE const & x) { RA_DEF_ASSIGNOPS_LINE(=); return *this; } \
  48. constexpr TYPE(TYPE && x) = default; \
  49. constexpr TYPE(TYPE const & x) = default;