[array/vector] Optimize range-based for-loop
Avoid bounds-checking.
diff --git a/src/hb-array.hh b/src/hb-array.hh
index 1c66f72..bd3d5af 100644
--- a/src/hb-array.hh
+++ b/src/hb-array.hh
@@ -104,6 +104,11 @@
bool operator != (const hb_array_t& o) const
{ return this->arrayZ != o.arrayZ || this->length != o.length; }
+ /* Faster range-based for loop without bounds-check. */
+ Type *begin () const { return arrayZ; }
+ Type *end () const { return arrayZ + length; }
+
+
/* Extra operators.
*/
Type * operator & () const { return arrayZ; }
diff --git a/src/hb-iter.hh b/src/hb-iter.hh
index 1a3ab43..b57f37b 100644
--- a/src/hb-iter.hh
+++ b/src/hb-iter.hh
@@ -73,8 +73,10 @@
/* Operators. */
iter_t iter () const { return *thiz(); }
iter_t operator + () const { return *thiz(); }
- iter_t begin () const { return *thiz(); }
- iter_t end () const { return thiz()->__end__ (); }
+ iter_t _begin () const { return *thiz(); }
+ iter_t begin () const { return _begin (); }
+ iter_t _end () const { return thiz()->__end__ (); }
+ iter_t end () const { return _end (); }
explicit operator bool () const { return thiz()->__more__ (); }
unsigned len () const { return thiz()->__len__ (); }
/* The following can only be enabled if item_t is reference type. Otherwise
@@ -118,7 +120,9 @@
#define HB_ITER_USING(Name) \
using item_t = typename Name::item_t; \
+ using Name::_begin; \
using Name::begin; \
+ using Name::_end; \
using Name::end; \
using Name::get_item_size; \
using Name::is_iterator; \
@@ -377,7 +381,7 @@
void __forward__ (unsigned n) { it += n; }
void __prev__ () { --it; }
void __rewind__ (unsigned n) { it -= n; }
- hb_map_iter_t __end__ () const { return hb_map_iter_t (it.end (), f); }
+ hb_map_iter_t __end__ () const { return hb_map_iter_t (it._end (), f); }
bool operator != (const hb_map_iter_t& o) const
{ return it != o.it; }
@@ -440,7 +444,7 @@
bool __more__ () const { return bool (it); }
void __next__ () { do ++it; while (it && !hb_has (p.get (), hb_get (f.get (), *it))); }
void __prev__ () { do --it; while (it && !hb_has (p.get (), hb_get (f.get (), *it))); }
- hb_filter_iter_t __end__ () const { return hb_filter_iter_t (it.end (), p, f); }
+ hb_filter_iter_t __end__ () const { return hb_filter_iter_t (it._end (), p, f); }
bool operator != (const hb_filter_iter_t& o) const
{ return it != o.it; }
@@ -553,7 +557,7 @@
void __forward__ (unsigned n) { a += n; b += n; }
void __prev__ () { --a; --b; }
void __rewind__ (unsigned n) { a -= n; b -= n; }
- hb_zip_iter_t __end__ () const { return hb_zip_iter_t (a.end (), b.end ()); }
+ hb_zip_iter_t __end__ () const { return hb_zip_iter_t (a._end (), b._end ()); }
/* Note, we should stop if ANY of the iters reaches end. As such two compare
* unequal if both items are unequal, NOT if either is unequal. */
bool operator != (const hb_zip_iter_t& o) const
@@ -637,7 +641,7 @@
}
}
- hb_concat_iter_t __end__ () const { return hb_concat_iter_t (a.end (), b.end ()); }
+ hb_concat_iter_t __end__ () const { return hb_concat_iter_t (a._end (), b._end ()); }
bool operator != (const hb_concat_iter_t& o) const
{
return a != o.a
diff --git a/src/hb-ot-map.cc b/src/hb-ot-map.cc
index 277167d..5811711 100644
--- a/src/hb-ot-map.cc
+++ b/src/hb-ot-map.cc
@@ -329,9 +329,8 @@
key.variations_index[table_index],
global_bit_mask);
- for (unsigned i = 0; i < m.features.length; i++)
+ for (auto &feature : m.features)
{
- auto &feature = m.features[i];
if (feature.stage[table_index] == stage)
add_lookups (m, table_index,
feature.index[table_index],
diff --git a/src/hb-vector.hh b/src/hb-vector.hh
index f9c7cf7..9a52f90 100644
--- a/src/hb-vector.hh
+++ b/src/hb-vector.hh
@@ -169,6 +169,11 @@
operator iter_t () const { return iter (); }
operator writer_t () { return writer (); }
+ /* Faster range-based for loop without bounds-check. */
+ Type *begin () const { return arrayZ; }
+ Type *end () const { return arrayZ + length; }
+
+
hb_sorted_array_t<Type> as_sorted_array ()
{ return hb_sorted_array (arrayZ, length); }
hb_sorted_array_t<const Type> as_sorted_array () const