QVarLengthArray: simplify / optimize assign(It, It)
After many failed attempts at addressing my dissatisfaction with the if (n) checks, I finally realized that the problem is the while (first != last && end != end()) loop, which, when exited, gives no indication as to _why_ it was exited. Any attempt to re-construct the exit condition must needs re-check something that should be known already. To fix, then, use a while (true) loop and react on first == last and dst == end() separately. As a drive-by, cache end(). Task-number: QTBUG-106200 Change-Id: Ic873774451df4102163e6e65d93c35e5dcbbb037 Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
This commit is contained in:
parent
5a3ac484db
commit
87e90a265f
@ -790,27 +790,28 @@ Q_OUTOFLINE_TEMPLATE void QVLABase<T>::assign_impl(qsizetype prealloc, void *arr
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto dst = begin();
|
auto dst = begin();
|
||||||
while (first != last && dst != end()) {
|
const auto dend = end();
|
||||||
*dst = *first; // reuse initialized buffer
|
while (true) {
|
||||||
|
if (first == last) { // ran out of elements to assign
|
||||||
|
std::destroy(dst, dend);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (dst == dend) { // ran out of existing elements to overwrite
|
||||||
|
if constexpr (IsFwdIt) {
|
||||||
|
dst = std::uninitialized_copy(first, last, dst);
|
||||||
|
break;
|
||||||
|
} else {
|
||||||
|
do {
|
||||||
|
emplace_back_impl(prealloc, array, *first);
|
||||||
|
} while (++first != last);
|
||||||
|
return; // size() is already correct (and dst invalidated)!
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*dst = *first; // overwrite existing element
|
||||||
++dst;
|
++dst;
|
||||||
++first;
|
++first;
|
||||||
}
|
}
|
||||||
|
this->s = dst - begin();
|
||||||
qsizetype n;
|
|
||||||
if constexpr (IsFwdIt) {
|
|
||||||
dst = std::uninitialized_copy(first, last, dst);
|
|
||||||
n = dst - begin();
|
|
||||||
if (n > s) // otherwise: readjust 's' in erase() later
|
|
||||||
s = n;
|
|
||||||
} else {
|
|
||||||
n = dst - begin();
|
|
||||||
while (first != last) {
|
|
||||||
emplace_back_impl(prealloc, array, *first);
|
|
||||||
++first;
|
|
||||||
++n;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
erase(data() + n, data() + size());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class T>
|
template <class T>
|
||||||
|
Loading…
Reference in New Issue
Block a user