sparse set: added reverse iterators

This commit is contained in:
Michele Caini
2020-07-29 18:50:31 +02:00
parent 70a3d62c14
commit 75dd86e8ef
2 changed files with 74 additions and 8 deletions

View File

@@ -180,6 +180,8 @@ public:
using size_type = std::size_t;
/*! @brief Random access iterator type. */
using iterator = sparse_set_iterator;
/*! @brief Reverse iterator type. */
using reverse_iterator = const entity_type *;
/*! @brief Default constructor. */
sparse_set() = default;
@@ -284,10 +286,6 @@ public:
* array. If the sparse set is empty, the returned iterator will be equal to
* `end()`.
*
* @note
* Random access iterators stay true to the order imposed by a call to
* `respect`.
*
* @return An iterator to the first entity of the internal packed array.
*/
[[nodiscard]] iterator begin() const ENTT_NOEXCEPT {
@@ -302,10 +300,6 @@ public:
* the internal packed array. Attempting to dereference the returned
* iterator results in undefined behavior.
*
* @note
* Random access iterators stay true to the order imposed by a call to
* `respect`.
*
* @return An iterator to the element following the last entity of the
* internal packed array.
*/
@@ -313,6 +307,34 @@ public:
return iterator{packed, {}};
}
/**
* @brief Returns a reverse iterator to the beginning.
*
* The returned iterator points to the first entity of the reversed internal
* packed array. If the sparse set is empty, the returned iterator will be
* equal to `rend()`.
*
* @return An iterator to the first entity of the reversed internal packed
* array.
*/
[[nodiscard]] reverse_iterator rbegin() const ENTT_NOEXCEPT {
return packed.data();
}
/**
* @brief Returns a reverse iterator to the end.
*
* The returned iterator points to the element following the last entity in
* the reversed internal packed array. Attempting to dereference the
* returned iterator results in undefined behavior.
*
* @return An iterator to the element following the last entity of the
* reversed internal packed array.
*/
[[nodiscard]] reverse_iterator rend() const ENTT_NOEXCEPT {
return rbegin() + packed.size();
}
/**
* @brief Finds an entity.
* @param entt A valid entity identifier.

View File

@@ -183,6 +183,50 @@ TEST(SparseSet, Iterator) {
ASSERT_EQ(*begin.operator->(), entt::entity{3});
}
TEST(SparseSet, ReverseIterator) {
using reverse_iterator = typename entt::sparse_set<entt::entity>::reverse_iterator;
entt::sparse_set<entt::entity> set;
set.emplace(entt::entity{3});
reverse_iterator end{set.rbegin()};
reverse_iterator begin{};
begin = set.rend();
std::swap(begin, end);
ASSERT_EQ(begin, set.rbegin());
ASSERT_EQ(end, set.rend());
ASSERT_NE(begin, end);
ASSERT_EQ(begin++, set.rbegin());
ASSERT_EQ(begin--, set.rend());
ASSERT_EQ(begin+1, set.rend());
ASSERT_EQ(end-1, set.rbegin());
ASSERT_EQ(++begin, set.rend());
ASSERT_EQ(--begin, set.rbegin());
ASSERT_EQ(begin += 1, set.rend());
ASSERT_EQ(begin -= 1, set.rbegin());
ASSERT_EQ(begin + (end - begin), set.rend());
ASSERT_EQ(begin - (begin - end), set.rend());
ASSERT_EQ(end - (end - begin), set.rbegin());
ASSERT_EQ(end + (begin - end), set.rbegin());
ASSERT_EQ(begin[0], *set.rbegin());
ASSERT_LT(begin, end);
ASSERT_LE(begin, set.rbegin());
ASSERT_GT(end, begin);
ASSERT_GE(end, set.rend());
ASSERT_EQ(*begin, entt::entity{3});
}
TEST(SparseSet, Find) {
entt::sparse_set<entt::entity> set;
set.emplace(entt::entity{3});