From 50dc3e7d9f4f290c7353313c5e5f888cb7c4846d Mon Sep 17 00:00:00 2001 From: Behdad Esfahbod Date: Wed, 8 May 2019 10:35:02 -0700 Subject: [PATCH] Add hb_iota() --- src/hb-iter.hh | 51 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/test-iter.cc | 10 ++++++++++ 2 files changed, 61 insertions(+) diff --git a/src/hb-iter.hh b/src/hb-iter.hh index 23d2c27..1a3e2ab 100644 --- a/src/hb-iter.hh +++ b/src/hb-iter.hh @@ -570,6 +570,57 @@ struct } HB_FUNCOBJ (hb_apply); +/* hb_iota() */ + +template +struct hb_iota_iter_t : + hb_iter_t, T> +{ + hb_iota_iter_t (T start, T end, S step) : v (start), end (end_for (start, end, step)), step (step) {} + + typedef T __item_t__; + static constexpr bool is_random_access_iterator = true; + static constexpr bool is_sorted_iterator = true; + __item_t__ __item__ () const { return v; } + __item_t__ __item_at__ (unsigned j) const { return v + j * step; } + bool __more__ () const { return v != end; } + unsigned __len__ () const { return (end - v) / step; } + void __next__ () { v += step; } + void __forward__ (unsigned n) { v += n * step; } + void __prev__ () { v -= step; } + void __rewind__ (unsigned n) { v -= n * step; } + hb_iota_iter_t __end__ () const { hb_iota_iter_t (end, end, step); } + bool operator != (const hb_iota_iter_t& o) const + { return v != o.v || end != o.end || step != o.step; } + + private: + static inline T end_for (T start, T end, S step) + { + auto res = (end - start) % step; + if (!res) + return end; + end += step - res; + return end; + } + + private: + T v; + T end; + S step; +}; +struct +{ + template hb_iota_iter_t + operator () (T end = (unsigned) -1) const + { return hb_iota_iter_t (0, end, 1u); } + + template hb_iota_iter_t + operator () (T start, T end, S&& step = 1u) const + { return hb_iota_iter_t (start, end, step); } +} +HB_FUNCOBJ (hb_iota); + + /* hb_sink() */ template diff --git a/src/test-iter.cc b/src/test-iter.cc index fe3c8f3..f29166f 100644 --- a/src/test-iter.cc +++ b/src/test-iter.cc @@ -236,5 +236,15 @@ main (int argc, char **argv) long vl; s >> vl; + hb_iota (); + assert (hb_iota (9).len () == 9); + assert (hb_iota (2, 9).len () == 7); + assert (hb_iota (2, 9, 3).len () == 3); + assert (hb_iota (2, 8, 3).len () == 2); + assert (hb_iota (2, 7, 3).len () == 2); + assert (hb_iota (-2, -9, -3).len () == 3); + assert (hb_iota (-2, -8, -3).len () == 2); + assert (hb_iota (-2, -7, -3).len () == 2); + return 0; } -- 2.7.4