queue.h 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104
  1. #ifndef HV_QUEUE_H_
  2. #define HV_QUEUE_H_
  3. /*
  4. * queue
  5. * FIFO: push_back,pop_front
  6. * stack
  7. * LIFO: push_back,pop_back
  8. */
  9. #include <assert.h> // for assert
  10. #include <stdlib.h> // for malloc,realloc,free
  11. #include <string.h> // for memset,memmove
  12. #include "hbase.h"
  13. #define QUEUE_INIT_SIZE 16
  14. // #include <deque>
  15. // typedef std::deque<type> qtype;
  16. #define QUEUE_DECL(type, qtype) \
  17. struct qtype { \
  18. type* ptr; \
  19. size_t size; \
  20. size_t maxsize;\
  21. size_t _offset;\
  22. }; \
  23. typedef struct qtype qtype;\
  24. \
  25. static inline type* qtype##_data(qtype* p) {\
  26. return p->ptr + p->_offset;\
  27. }\
  28. \
  29. static inline int qtype##_size(qtype* p) {\
  30. return p->size;\
  31. }\
  32. \
  33. static inline int qtype##_maxsize(qtype* p) {\
  34. return p->maxsize;\
  35. }\
  36. \
  37. static inline int qtype##_empty(qtype* p) {\
  38. return p->size == 0;\
  39. }\
  40. \
  41. static inline type* qtype##_front(qtype* p) {\
  42. return p->size == 0 ? NULL : p->ptr + p->_offset;\
  43. }\
  44. \
  45. static inline type* qtype##_back(qtype* p) {\
  46. return p->size == 0 ? NULL : p->ptr + p->_offset + p->size-1;\
  47. }\
  48. \
  49. static inline void qtype##_init(qtype* p, int maxsize) {\
  50. p->_offset = 0;\
  51. p->size = 0;\
  52. p->maxsize = maxsize;\
  53. SAFE_ALLOC(p->ptr, sizeof(type) * maxsize);\
  54. }\
  55. \
  56. static inline void qtype##_clear(qtype* p) {\
  57. p->_offset = 0;\
  58. p->size = 0;\
  59. memset(p->ptr, 0, sizeof(type) * p->maxsize);\
  60. }\
  61. \
  62. static inline void qtype##_cleanup(qtype* p) {\
  63. SAFE_FREE(p->ptr);\
  64. p->_offset = p->size = p->maxsize = 0;\
  65. }\
  66. \
  67. static inline void qtype##_resize(qtype* p, int maxsize) {\
  68. if (maxsize == 0) maxsize = QUEUE_INIT_SIZE;\
  69. p->ptr = (type*)safe_realloc(p->ptr, sizeof(type)*maxsize, sizeof(type)*p->maxsize);\
  70. p->maxsize = maxsize;\
  71. }\
  72. \
  73. static inline void qtype##_double_resize(qtype* p) {\
  74. return qtype##_resize(p, p->maxsize*2);\
  75. }\
  76. \
  77. static inline void qtype##_push_back(qtype* p, type* elem) {\
  78. if (p->size == p->maxsize) {\
  79. qtype##_double_resize(p);\
  80. }\
  81. else if (p->_offset + p->size == p->maxsize) {\
  82. memmove(p->ptr, p->ptr + p->_offset, p->size);\
  83. p->_offset = 0;\
  84. }\
  85. p->ptr[p->_offset + p->size] = *elem;\
  86. p->size++;\
  87. }\
  88. static inline void qtype##_pop_front(qtype* p) {\
  89. assert(p->size > 0);\
  90. p->size--;\
  91. if (++p->_offset == p->maxsize) p->_offset = 0;\
  92. }\
  93. \
  94. static inline void qtype##_pop_back(qtype* p) {\
  95. assert(p->size > 0);\
  96. p->size--;\
  97. }\
  98. #endif // HV_QUEUE_H_