diff --git a/core/math/a_star.cpp b/core/math/a_star.cpp index 3e537ae1809..80322432bdf 100644 --- a/core/math/a_star.cpp +++ b/core/math/a_star.cpp @@ -49,10 +49,9 @@ void AStar3D::add_point(int64_t p_id, const Vector3 &p_pos, real_t p_weight_scal ERR_FAIL_COND_MSG(p_id < 0, vformat("Can't add a point with negative id: %d.", p_id)); ERR_FAIL_COND_MSG(p_weight_scale < 0.0, vformat("Can't add a point with weight scale less than 0.0: %f.", p_weight_scale)); - Point *found_pt; - bool p_exists = points.lookup(p_id, found_pt); + Point **point_entry = points.getptr(p_id); - if (!p_exists) { + if (!point_entry) { Point *pt = memnew(Point); pt->id = p_id; pt->pos = p_pos; @@ -61,89 +60,86 @@ void AStar3D::add_point(int64_t p_id, const Vector3 &p_pos, real_t p_weight_scal pt->open_pass = 0; pt->closed_pass = 0; pt->enabled = true; - points.set(p_id, pt); + points.insert_new(p_id, pt); } else { + Point *found_pt = *point_entry; found_pt->pos = p_pos; found_pt->weight_scale = p_weight_scale; } } Vector3 AStar3D::get_point_position(int64_t p_id) const { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_V_MSG(!p_exists, Vector3(), vformat("Can't get point's position. Point with id: %d doesn't exist.", p_id)); + Point *const *point_entry = points.getptr(p_id); + ERR_FAIL_COND_V_MSG(!point_entry, Vector3(), vformat("Can't get point's position. Point with id: %d doesn't exist.", p_id)); - return p->pos; + return (*point_entry)->pos; } void AStar3D::set_point_position(int64_t p_id, const Vector3 &p_pos) { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_MSG(!p_exists, vformat("Can't set point's position. Point with id: %d doesn't exist.", p_id)); + Point **point_entry = points.getptr(p_id); + ERR_FAIL_COND_MSG(!point_entry, vformat("Can't set point's position. Point with id: %d doesn't exist.", p_id)); - p->pos = p_pos; + (*point_entry)->pos = p_pos; } real_t AStar3D::get_point_weight_scale(int64_t p_id) const { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_V_MSG(!p_exists, 0, vformat("Can't get point's weight scale. Point with id: %d doesn't exist.", p_id)); + Point *const *point_entry = points.getptr(p_id); + ERR_FAIL_COND_V_MSG(!point_entry, 0, vformat("Can't get point's weight scale. Point with id: %d doesn't exist.", p_id)); - return p->weight_scale; + return (*point_entry)->weight_scale; } void AStar3D::set_point_weight_scale(int64_t p_id, real_t p_weight_scale) { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_MSG(!p_exists, vformat("Can't set point's weight scale. Point with id: %d doesn't exist.", p_id)); + Point **point_entry = points.getptr(p_id); + ERR_FAIL_COND_MSG(!point_entry, vformat("Can't set point's weight scale. Point with id: %d doesn't exist.", p_id)); ERR_FAIL_COND_MSG(p_weight_scale < 0.0, vformat("Can't set point's weight scale less than 0.0: %f.", p_weight_scale)); - p->weight_scale = p_weight_scale; + (*point_entry)->weight_scale = p_weight_scale; } void AStar3D::remove_point(int64_t p_id) { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_MSG(!p_exists, vformat("Can't remove point. Point with id: %d doesn't exist.", p_id)); + Point **point_entry = points.getptr(p_id); + ERR_FAIL_COND_MSG(!point_entry, vformat("Can't remove point. Point with id: %d doesn't exist.", p_id)); + Point *p = *point_entry; - for (OAHashMap::Iterator it = p->neighbors.iter(); it.valid; it = p->neighbors.next_iter(it)) { - Segment s(p_id, (*it.key)); + for (KeyValue &kv : p->neighbors) { + Segment s(p_id, kv.key); segments.erase(s); - (*it.value)->neighbors.remove(p->id); - (*it.value)->unlinked_neighbours.remove(p->id); + kv.value->neighbors.erase(p->id); + kv.value->unlinked_neighbours.erase(p->id); } - for (OAHashMap::Iterator it = p->unlinked_neighbours.iter(); it.valid; it = p->unlinked_neighbours.next_iter(it)) { - Segment s(p_id, (*it.key)); + for (KeyValue &kv : p->unlinked_neighbours) { + Segment s(p_id, kv.key); segments.erase(s); - (*it.value)->neighbors.remove(p->id); - (*it.value)->unlinked_neighbours.remove(p->id); + kv.value->neighbors.erase(p->id); + kv.value->unlinked_neighbours.erase(p->id); } memdelete(p); - points.remove(p_id); + points.erase(p_id); last_free_id = p_id; } void AStar3D::connect_points(int64_t p_id, int64_t p_with_id, bool bidirectional) { ERR_FAIL_COND_MSG(p_id == p_with_id, vformat("Can't connect point with id: %d to itself.", p_id)); - Point *a = nullptr; - bool from_exists = points.lookup(p_id, a); - ERR_FAIL_COND_MSG(!from_exists, vformat("Can't connect points. Point with id: %d doesn't exist.", p_id)); + Point **a_entry = points.getptr(p_id); + ERR_FAIL_COND_MSG(!a_entry, vformat("Can't connect points. Point with id: %d doesn't exist.", p_id)); + Point *a = *a_entry; - Point *b = nullptr; - bool to_exists = points.lookup(p_with_id, b); - ERR_FAIL_COND_MSG(!to_exists, vformat("Can't connect points. Point with id: %d doesn't exist.", p_with_id)); + Point **b_entry = points.getptr(p_with_id); + ERR_FAIL_COND_MSG(!b_entry, vformat("Can't connect points. Point with id: %d doesn't exist.", p_with_id)); + Point *b = *b_entry; - a->neighbors.set(b->id, b); + a->neighbors.insert(b->id, b); if (bidirectional) { - b->neighbors.set(a->id, a); + b->neighbors.insert(a->id, a); } else { - b->unlinked_neighbours.set(a->id, a); + b->unlinked_neighbours.insert(a->id, a); } Segment s(p_id, p_with_id); @@ -156,8 +152,8 @@ void AStar3D::connect_points(int64_t p_id, int64_t p_with_id, bool bidirectional s.direction |= element->direction; if (s.direction == Segment::BIDIRECTIONAL) { // Both are neighbors of each other now - a->unlinked_neighbours.remove(b->id); - b->unlinked_neighbours.remove(a->id); + a->unlinked_neighbours.erase(b->id); + b->unlinked_neighbours.erase(a->id); } segments.remove(element); } @@ -166,13 +162,13 @@ void AStar3D::connect_points(int64_t p_id, int64_t p_with_id, bool bidirectional } void AStar3D::disconnect_points(int64_t p_id, int64_t p_with_id, bool bidirectional) { - Point *a = nullptr; - bool a_exists = points.lookup(p_id, a); - ERR_FAIL_COND_MSG(!a_exists, vformat("Can't disconnect points. Point with id: %d doesn't exist.", p_id)); + Point **a_entry = points.getptr(p_id); + ERR_FAIL_COND_MSG(!a_entry, vformat("Can't disconnect points. Point with id: %d doesn't exist.", p_id)); + Point *a = *a_entry; - Point *b = nullptr; - bool b_exists = points.lookup(p_with_id, b); - ERR_FAIL_COND_MSG(!b_exists, vformat("Can't disconnect points. Point with id: %d doesn't exist.", p_with_id)); + Point **b_entry = points.getptr(p_with_id); + ERR_FAIL_COND_MSG(!b_entry, vformat("Can't disconnect points. Point with id: %d doesn't exist.", p_with_id)); + Point *b = *b_entry; Segment s(p_id, p_with_id); int remove_direction = bidirectional ? (int)Segment::BIDIRECTIONAL : (int)s.direction; @@ -183,18 +179,18 @@ void AStar3D::disconnect_points(int64_t p_id, int64_t p_with_id, bool bidirectio // Erase the directions to be removed s.direction = (element->direction & ~remove_direction); - a->neighbors.remove(b->id); + a->neighbors.erase(b->id); if (bidirectional) { - b->neighbors.remove(a->id); + b->neighbors.erase(a->id); if (element->direction != Segment::BIDIRECTIONAL) { - a->unlinked_neighbours.remove(b->id); - b->unlinked_neighbours.remove(a->id); + a->unlinked_neighbours.erase(b->id); + b->unlinked_neighbours.erase(a->id); } } else { if (s.direction == Segment::NONE) { - b->unlinked_neighbours.remove(a->id); + b->unlinked_neighbours.erase(a->id); } else { - a->unlinked_neighbours.set(b->id, b); + a->unlinked_neighbours.insert(b->id, b); } } @@ -212,22 +208,21 @@ bool AStar3D::has_point(int64_t p_id) const { PackedInt64Array AStar3D::get_point_ids() { PackedInt64Array point_list; - for (OAHashMap::Iterator it = points.iter(); it.valid; it = points.next_iter(it)) { - point_list.push_back(*(it.key)); + for (KeyValue &kv : points) { + point_list.push_back(kv.key); } return point_list; } Vector AStar3D::get_point_connections(int64_t p_id) { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_V_MSG(!p_exists, Vector(), vformat("Can't get point's connections. Point with id: %d doesn't exist.", p_id)); + Point **p_entry = points.getptr(p_id); + ERR_FAIL_COND_V_MSG(!p_entry, Vector(), vformat("Can't get point's connections. Point with id: %d doesn't exist.", p_id)); Vector point_list; - for (OAHashMap::Iterator it = p->neighbors.iter(); it.valid; it = p->neighbors.next_iter(it)) { - point_list.push_back((*it.key)); + for (KeyValue &kv : (*p_entry)->neighbors) { + point_list.push_back(kv.key); } return point_list; @@ -243,15 +238,15 @@ bool AStar3D::are_points_connected(int64_t p_id, int64_t p_with_id, bool bidirec void AStar3D::clear() { last_free_id = 0; - for (OAHashMap::Iterator it = points.iter(); it.valid; it = points.next_iter(it)) { - memdelete(*(it.value)); + for (KeyValue &kv : points) { + memdelete(kv.value); } segments.clear(); points.clear(); } int64_t AStar3D::get_point_count() const { - return points.get_num_elements(); + return points.size(); } int64_t AStar3D::get_point_capacity() const { @@ -267,15 +262,15 @@ int64_t AStar3D::get_closest_point(const Vector3 &p_point, bool p_include_disabl int64_t closest_id = -1; real_t closest_dist = 1e20; - for (OAHashMap::Iterator it = points.iter(); it.valid; it = points.next_iter(it)) { - if (!p_include_disabled && !(*it.value)->enabled) { + for (const KeyValue &kv : points) { + if (!p_include_disabled && !kv.value->enabled) { continue; // Disabled points should not be considered. } // Keep the closest point's ID, and in case of multiple closest IDs, // the smallest one (makes it deterministic). - real_t d = p_point.distance_squared_to((*it.value)->pos); - int64_t id = *(it.key); + real_t d = p_point.distance_squared_to(kv.value->pos); + int64_t id = kv.key; if (d <= closest_dist) { if (d == closest_dist && id > closest_id) { // Keep lowest ID. continue; @@ -293,9 +288,8 @@ Vector3 AStar3D::get_closest_position_in_segment(const Vector3 &p_point) const { Vector3 closest_point; for (const Segment &E : segments) { - Point *from_point = nullptr, *to_point = nullptr; - points.lookup(E.key.first, from_point); - points.lookup(E.key.second, to_point); + const Point *from_point = *points.getptr(E.key.first); + const Point *to_point = *points.getptr(E.key.second); if (!(from_point->enabled && to_point->enabled)) { continue; @@ -348,8 +342,8 @@ bool AStar3D::_solve(Point *begin_point, Point *end_point, bool p_allow_partial_ open_list.remove_at(open_list.size() - 1); p->closed_pass = pass; // Mark the point as closed. - for (OAHashMap::Iterator it = p->neighbors.iter(); it.valid; it = p->neighbors.next_iter(it)) { - Point *e = *(it.value); // The neighbor point. + for (const KeyValue &kv : p->neighbors) { + Point *e = kv.value; // The neighbor point. if (!e->enabled || e->closed_pass == pass) { continue; @@ -390,13 +384,13 @@ real_t AStar3D::_estimate_cost(int64_t p_from_id, int64_t p_end_id) { return scost; } - Point *from_point = nullptr; - bool from_exists = points.lookup(p_from_id, from_point); - ERR_FAIL_COND_V_MSG(!from_exists, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_from_id)); + Point **from_entry = points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!from_entry, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_from_id)); + Point *from_point = *from_entry; - Point *end_point = nullptr; - bool end_exists = points.lookup(p_end_id, end_point); - ERR_FAIL_COND_V_MSG(!end_exists, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_end_id)); + Point **end_entry = points.getptr(p_end_id); + ERR_FAIL_COND_V_MSG(!end_entry, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_end_id)); + Point *end_point = *end_entry; return from_point->pos.distance_to(end_point->pos); } @@ -407,25 +401,25 @@ real_t AStar3D::_compute_cost(int64_t p_from_id, int64_t p_to_id) { return scost; } - Point *from_point = nullptr; - bool from_exists = points.lookup(p_from_id, from_point); - ERR_FAIL_COND_V_MSG(!from_exists, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_from_id)); + Point **from_entry = points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!from_entry, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_from_id)); + Point *from_point = *from_entry; - Point *to_point = nullptr; - bool to_exists = points.lookup(p_to_id, to_point); - ERR_FAIL_COND_V_MSG(!to_exists, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_to_id)); + Point **to_entry = points.getptr(p_to_id); + ERR_FAIL_COND_V_MSG(!to_entry, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_to_id)); + Point *to_point = *to_entry; return from_point->pos.distance_to(to_point->pos); } Vector AStar3D::get_point_path(int64_t p_from_id, int64_t p_to_id, bool p_allow_partial_path) { - Point *a = nullptr; - bool from_exists = points.lookup(p_from_id, a); - ERR_FAIL_COND_V_MSG(!from_exists, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_from_id)); + Point **a_entry = points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!a_entry, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_from_id)); + Point *a = *a_entry; - Point *b = nullptr; - bool to_exists = points.lookup(p_to_id, b); - ERR_FAIL_COND_V_MSG(!to_exists, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_to_id)); + Point **b_entry = points.getptr(p_to_id); + ERR_FAIL_COND_V_MSG(!b_entry, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_to_id)); + Point *b = *b_entry; if (a == b) { Vector ret; @@ -473,13 +467,13 @@ Vector AStar3D::get_point_path(int64_t p_from_id, int64_t p_to_id, bool } Vector AStar3D::get_id_path(int64_t p_from_id, int64_t p_to_id, bool p_allow_partial_path) { - Point *a = nullptr; - bool from_exists = points.lookup(p_from_id, a); - ERR_FAIL_COND_V_MSG(!from_exists, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_from_id)); + Point **a_entry = points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!a_entry, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_from_id)); + Point *a = *a_entry; - Point *b = nullptr; - bool to_exists = points.lookup(p_to_id, b); - ERR_FAIL_COND_V_MSG(!to_exists, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_to_id)); + Point **b_entry = points.getptr(p_to_id); + ERR_FAIL_COND_V_MSG(!b_entry, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_to_id)); + Point *b = *b_entry; if (a == b) { Vector ret; @@ -527,17 +521,17 @@ Vector AStar3D::get_id_path(int64_t p_from_id, int64_t p_to_id, bool p_ } void AStar3D::set_point_disabled(int64_t p_id, bool p_disabled) { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_MSG(!p_exists, vformat("Can't set if point is disabled. Point with id: %d doesn't exist.", p_id)); + Point **p_entry = points.getptr(p_id); + ERR_FAIL_COND_MSG(!p_entry, vformat("Can't set if point is disabled. Point with id: %d doesn't exist.", p_id)); + Point *p = *p_entry; p->enabled = !p_disabled; } bool AStar3D::is_point_disabled(int64_t p_id) const { - Point *p = nullptr; - bool p_exists = points.lookup(p_id, p); - ERR_FAIL_COND_V_MSG(!p_exists, false, vformat("Can't get if point is disabled. Point with id: %d doesn't exist.", p_id)); + Point *const *p_entry = points.getptr(p_id); + ERR_FAIL_COND_V_MSG(!p_entry, false, vformat("Can't get if point is disabled. Point with id: %d doesn't exist.", p_id)); + Point *p = *p_entry; return !p->enabled; } @@ -674,13 +668,13 @@ real_t AStar2D::_estimate_cost(int64_t p_from_id, int64_t p_end_id) { return scost; } - AStar3D::Point *from_point = nullptr; - bool from_exists = astar.points.lookup(p_from_id, from_point); - ERR_FAIL_COND_V_MSG(!from_exists, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point **from_entry = astar.points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!from_entry, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point *from_point = *from_entry; - AStar3D::Point *end_point = nullptr; - bool to_exists = astar.points.lookup(p_end_id, end_point); - ERR_FAIL_COND_V_MSG(!to_exists, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_end_id)); + AStar3D::Point **end_entry = astar.points.getptr(p_end_id); + ERR_FAIL_COND_V_MSG(!end_entry, 0, vformat("Can't estimate cost. Point with id: %d doesn't exist.", p_end_id)); + AStar3D::Point *end_point = *end_entry; return from_point->pos.distance_to(end_point->pos); } @@ -691,25 +685,25 @@ real_t AStar2D::_compute_cost(int64_t p_from_id, int64_t p_to_id) { return scost; } - AStar3D::Point *from_point = nullptr; - bool from_exists = astar.points.lookup(p_from_id, from_point); - ERR_FAIL_COND_V_MSG(!from_exists, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point **from_entry = astar.points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!from_entry, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point *from_point = *from_entry; - AStar3D::Point *to_point = nullptr; - bool to_exists = astar.points.lookup(p_to_id, to_point); - ERR_FAIL_COND_V_MSG(!to_exists, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_to_id)); + AStar3D::Point **to_entry = astar.points.getptr(p_to_id); + ERR_FAIL_COND_V_MSG(!to_entry, 0, vformat("Can't compute cost. Point with id: %d doesn't exist.", p_to_id)); + AStar3D::Point *to_point = *to_entry; return from_point->pos.distance_to(to_point->pos); } Vector AStar2D::get_point_path(int64_t p_from_id, int64_t p_to_id, bool p_allow_partial_path) { - AStar3D::Point *a = nullptr; - bool from_exists = astar.points.lookup(p_from_id, a); - ERR_FAIL_COND_V_MSG(!from_exists, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point **a_entry = astar.points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!a_entry, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point *a = *a_entry; - AStar3D::Point *b = nullptr; - bool to_exists = astar.points.lookup(p_to_id, b); - ERR_FAIL_COND_V_MSG(!to_exists, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_to_id)); + AStar3D::Point **b_entry = astar.points.getptr(p_to_id); + ERR_FAIL_COND_V_MSG(!b_entry, Vector(), vformat("Can't get point path. Point with id: %d doesn't exist.", p_to_id)); + AStar3D::Point *b = *b_entry; if (a == b) { Vector ret = { Vector2(a->pos.x, a->pos.y) }; @@ -756,13 +750,13 @@ Vector AStar2D::get_point_path(int64_t p_from_id, int64_t p_to_id, bool } Vector AStar2D::get_id_path(int64_t p_from_id, int64_t p_to_id, bool p_allow_partial_path) { - AStar3D::Point *a = nullptr; - bool from_exists = astar.points.lookup(p_from_id, a); - ERR_FAIL_COND_V_MSG(!from_exists, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point **a_entry = astar.points.getptr(p_from_id); + ERR_FAIL_COND_V_MSG(!a_entry, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_from_id)); + AStar3D::Point *a = *a_entry; - AStar3D::Point *b = nullptr; - bool to_exists = astar.points.lookup(p_to_id, b); - ERR_FAIL_COND_V_MSG(!to_exists, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_to_id)); + AStar3D::Point **to_entry = astar.points.getptr(p_to_id); + ERR_FAIL_COND_V_MSG(!to_entry, Vector(), vformat("Can't get id path. Point with id: %d doesn't exist.", p_to_id)); + AStar3D::Point *b = *to_entry; if (a == b) { Vector ret; @@ -845,8 +839,8 @@ bool AStar2D::_solve(AStar3D::Point *begin_point, AStar3D::Point *end_point, boo open_list.remove_at(open_list.size() - 1); p->closed_pass = astar.pass; // Mark the point as closed. - for (OAHashMap::Iterator it = p->neighbors.iter(); it.valid; it = p->neighbors.next_iter(it)) { - AStar3D::Point *e = *(it.value); // The neighbor point. + for (KeyValue &kv : p->neighbors) { + AStar3D::Point *e = kv.value; // The neighbor point. if (!e->enabled || e->closed_pass == astar.pass) { continue; diff --git a/core/math/a_star.h b/core/math/a_star.h index 1351dd5b569..87980021ef4 100644 --- a/core/math/a_star.h +++ b/core/math/a_star.h @@ -32,7 +32,7 @@ #include "core/object/gdvirtual.gen.inc" #include "core/object/ref_counted.h" -#include "core/templates/oa_hash_map.h" +#include "core/templates/a_hash_map.h" /** A* pathfinding algorithm. @@ -50,8 +50,8 @@ class AStar3D : public RefCounted { real_t weight_scale = 0; bool enabled = false; - OAHashMap neighbors = 4u; - OAHashMap unlinked_neighbours = 4u; + AHashMap neighbors = 4u; + AHashMap unlinked_neighbours = 4u; // Used for pathfinding. Point *prev_point = nullptr; @@ -110,7 +110,7 @@ class AStar3D : public RefCounted { mutable int64_t last_free_id = 0; uint64_t pass = 1; - OAHashMap points; + AHashMap points; HashSet segments; Point *last_closest_point = nullptr; diff --git a/core/math/convex_hull.cpp b/core/math/convex_hull.cpp index 9f8dccf5f0c..87f0652cc18 100644 --- a/core/math/convex_hull.cpp +++ b/core/math/convex_hull.cpp @@ -61,7 +61,7 @@ subject to the following restrictions: #include "core/error/error_macros.h" #include "core/math/aabb.h" #include "core/math/math_defs.h" -#include "core/templates/oa_hash_map.h" +#include "core/templates/a_hash_map.h" #include "core/templates/paged_allocator.h" //#define DEBUG_CONVEX_HULL @@ -2267,7 +2267,7 @@ Error ConvexHullComputer::convex_hull(const Vector &p_points, Geometry3 // Copy the edges over. There's two "half-edges" for every edge, so we pick only one of them. r_mesh.edges.resize(ch.edges.size() / 2); - OAHashMap edge_map(ch.edges.size() * 4); // The higher the capacity, the faster the insert + AHashMap edge_map(ch.edges.size() * 4); // The higher the capacity, the faster the insert uint32_t edges_copied = 0; for (uint32_t i = 0; i < ch.edges.size(); i++) { @@ -2292,11 +2292,11 @@ Error ConvexHullComputer::convex_hull(const Vector &p_points, Geometry3 uint64_t key = b; key <<= 32; key |= a; - int32_t index; - if (!edge_map.lookup(key, index)) { + int32_t *index_ptr = edge_map.getptr(key); + if (!index_ptr) { ERR_PRINT("Invalid edge"); } else { - r_mesh.edges[index].face_b = edge_faces[i]; + r_mesh.edges[*index_ptr].face_b = edge_faces[i]; } } } diff --git a/core/math/delaunay_3d.h b/core/math/delaunay_3d.h index 122ff945f13..a4b274ddf19 100644 --- a/core/math/delaunay_3d.h +++ b/core/math/delaunay_3d.h @@ -33,9 +33,9 @@ #include "core/math/aabb.h" #include "core/math/projection.h" #include "core/math/vector3.h" +#include "core/templates/a_hash_map.h" #include "core/templates/list.h" #include "core/templates/local_vector.h" -#include "core/templates/oa_hash_map.h" #include "core/templates/vector.h" #include "thirdparty/misc/r128.h" @@ -260,7 +260,7 @@ public: circum_sphere_compute(points, root); } - OAHashMap triangles_inserted; + AHashMap triangles_inserted; LocalVector triangles; for (uint32_t i = 0; i < point_count; i++) { @@ -293,7 +293,7 @@ public: for (uint32_t k = 0; k < 4; k++) { Triangle t = Triangle(simplex->points[triangle_order[k][0]], simplex->points[triangle_order[k][1]], simplex->points[triangle_order[k][2]]); - uint32_t *p = triangles_inserted.lookup_ptr(t); + uint32_t *p = triangles_inserted.getptr(t); if (p) { // This Delaunay implementation uses the Bowyer-Watson algorithm. // The rule is that you don't reuse any triangles that were diff --git a/core/templates/oa_hash_map.h b/core/templates/oa_hash_map.h deleted file mode 100644 index ce6813b3f19..00000000000 --- a/core/templates/oa_hash_map.h +++ /dev/null @@ -1,402 +0,0 @@ -/**************************************************************************/ -/* oa_hash_map.h */ -/**************************************************************************/ -/* This file is part of: */ -/* GODOT ENGINE */ -/* https://godotengine.org */ -/**************************************************************************/ -/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */ -/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */ -/* */ -/* Permission is hereby granted, free of charge, to any person obtaining */ -/* a copy of this software and associated documentation files (the */ -/* "Software"), to deal in the Software without restriction, including */ -/* without limitation the rights to use, copy, modify, merge, publish, */ -/* distribute, sublicense, and/or sell copies of the Software, and to */ -/* permit persons to whom the Software is furnished to do so, subject to */ -/* the following conditions: */ -/* */ -/* The above copyright notice and this permission notice shall be */ -/* included in all copies or substantial portions of the Software. */ -/* */ -/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ -/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ -/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */ -/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ -/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ -/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ -/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ -/**************************************************************************/ - -#pragma once - -#include "core/os/memory.h" -#include "core/templates/hashfuncs.h" -#include "core/templates/pair.h" - -/** - * A HashMap implementation that uses open addressing with Robin Hood hashing. - * Robin Hood hashing swaps out entries that have a smaller probing distance - * than the to-be-inserted entry, that evens out the average probing distance - * and enables faster lookups. Backward shift deletion is employed to further - * improve the performance and to avoid infinite loops in rare cases. - * - * The entries are stored inplace, so huge keys or values might fill cache lines - * a lot faster. - * - * Only used keys and values are constructed. For free positions there's space - * in the arrays for each, but that memory is kept uninitialized. - * - * The assignment operator copy the pairs from one map to the other. - */ -template > -class OAHashMap { -private: - TValue *values = nullptr; - TKey *keys = nullptr; - uint32_t *hashes = nullptr; - - uint32_t capacity = 0; - - uint32_t num_elements = 0; - - static const uint32_t EMPTY_HASH = 0; - - _FORCE_INLINE_ uint32_t _hash(const TKey &p_key) const { - uint32_t hash = Hasher::hash(p_key); - - if (hash == EMPTY_HASH) { - hash = EMPTY_HASH + 1; - } - - return hash; - } - - _FORCE_INLINE_ uint32_t _get_probe_length(uint32_t p_pos, uint32_t p_hash) const { - uint32_t original_pos = p_hash % capacity; - return (p_pos - original_pos + capacity) % capacity; - } - - _FORCE_INLINE_ void _construct(uint32_t p_pos, uint32_t p_hash, const TKey &p_key, const TValue &p_value) { - memnew_placement(&keys[p_pos], TKey(p_key)); - memnew_placement(&values[p_pos], TValue(p_value)); - hashes[p_pos] = p_hash; - - num_elements++; - } - - bool _lookup_pos(const TKey &p_key, uint32_t &r_pos) const { - uint32_t hash = _hash(p_key); - uint32_t pos = hash % capacity; - uint32_t distance = 0; - - while (true) { - if (hashes[pos] == EMPTY_HASH) { - return false; - } - - if (distance > _get_probe_length(pos, hashes[pos])) { - return false; - } - - if (hashes[pos] == hash && Comparator::compare(keys[pos], p_key)) { - r_pos = pos; - return true; - } - - pos = (pos + 1) % capacity; - distance++; - } - } - - void _insert_with_hash(uint32_t p_hash, const TKey &p_key, const TValue &p_value) { - uint32_t hash = p_hash; - uint32_t distance = 0; - uint32_t pos = hash % capacity; - - TKey key = p_key; - TValue value = p_value; - - while (true) { - if (hashes[pos] == EMPTY_HASH) { - _construct(pos, hash, key, value); - - return; - } - - // not an empty slot, let's check the probing length of the existing one - uint32_t existing_probe_len = _get_probe_length(pos, hashes[pos]); - if (existing_probe_len < distance) { - SWAP(hash, hashes[pos]); - SWAP(key, keys[pos]); - SWAP(value, values[pos]); - distance = existing_probe_len; - } - - pos = (pos + 1) % capacity; - distance++; - } - } - - void _resize_and_rehash(uint32_t p_new_capacity) { - uint32_t old_capacity = capacity; - - // Capacity can't be 0. - capacity = MAX(1u, p_new_capacity); - - TKey *old_keys = keys; - TValue *old_values = values; - uint32_t *old_hashes = hashes; - - num_elements = 0; - keys = static_cast(Memory::alloc_static(sizeof(TKey) * capacity)); - values = static_cast(Memory::alloc_static(sizeof(TValue) * capacity)); - static_assert(EMPTY_HASH == 0, "Assuming EMPTY_HASH = 0 for alloc_static_zeroed call"); - hashes = static_cast(Memory::alloc_static_zeroed(sizeof(uint32_t) * capacity)); - - if (old_capacity == 0) { - // Nothing to do. - return; - } - - for (uint32_t i = 0; i < old_capacity; i++) { - if (old_hashes[i] == EMPTY_HASH) { - continue; - } - - _insert_with_hash(old_hashes[i], old_keys[i], old_values[i]); - - old_keys[i].~TKey(); - old_values[i].~TValue(); - } - - Memory::free_static(old_keys); - Memory::free_static(old_values); - Memory::free_static(old_hashes); - } - - void _resize_and_rehash() { - _resize_and_rehash(capacity * 2); - } - -public: - _FORCE_INLINE_ uint32_t get_capacity() const { return capacity; } - _FORCE_INLINE_ uint32_t get_num_elements() const { return num_elements; } - - bool is_empty() const { - return num_elements == 0; - } - - void clear() { - for (uint32_t i = 0; i < capacity; i++) { - if (hashes[i] == EMPTY_HASH) { - continue; - } - - hashes[i] = EMPTY_HASH; - values[i].~TValue(); - keys[i].~TKey(); - } - - num_elements = 0; - } - - void insert(const TKey &p_key, const TValue &p_value) { - if (num_elements + 1 > 0.9 * capacity) { - _resize_and_rehash(); - } - - uint32_t hash = _hash(p_key); - - _insert_with_hash(hash, p_key, p_value); - } - - void set(const TKey &p_key, const TValue &p_data) { - uint32_t pos = 0; - bool exists = _lookup_pos(p_key, pos); - - if (exists) { - values[pos] = p_data; - } else { - insert(p_key, p_data); - } - } - - /** - * returns true if the value was found, false otherwise. - * - * if r_data is not nullptr then the value will be written to the object - * it points to. - */ - bool lookup(const TKey &p_key, TValue &r_data) const { - uint32_t pos = 0; - bool exists = _lookup_pos(p_key, pos); - - if (exists) { - r_data = values[pos]; - return true; - } - - return false; - } - - const TValue *lookup_ptr(const TKey &p_key) const { - uint32_t pos = 0; - bool exists = _lookup_pos(p_key, pos); - - if (exists) { - return &values[pos]; - } - return nullptr; - } - - TValue *lookup_ptr(const TKey &p_key) { - uint32_t pos = 0; - bool exists = _lookup_pos(p_key, pos); - - if (exists) { - return &values[pos]; - } - return nullptr; - } - - _FORCE_INLINE_ bool has(const TKey &p_key) const { - uint32_t _pos = 0; - return _lookup_pos(p_key, _pos); - } - - void remove(const TKey &p_key) { - uint32_t pos = 0; - bool exists = _lookup_pos(p_key, pos); - - if (!exists) { - return; - } - - uint32_t next_pos = (pos + 1) % capacity; - while (hashes[next_pos] != EMPTY_HASH && - _get_probe_length(next_pos, hashes[next_pos]) != 0) { - SWAP(hashes[next_pos], hashes[pos]); - SWAP(keys[next_pos], keys[pos]); - SWAP(values[next_pos], values[pos]); - pos = next_pos; - next_pos = (pos + 1) % capacity; - } - - hashes[pos] = EMPTY_HASH; - values[pos].~TValue(); - keys[pos].~TKey(); - - num_elements--; - } - - /** - * reserves space for a number of elements, useful to avoid many resizes and rehashes - * if adding a known (possibly large) number of elements at once, must be larger than old - * capacity. - **/ - void reserve(uint32_t p_new_capacity) { - ERR_FAIL_COND_MSG(p_new_capacity < get_num_elements(), "reserve() called with a capacity smaller than the current size. This is likely a mistake."); - if (p_new_capacity <= capacity) { - return; - } - _resize_and_rehash(p_new_capacity); - } - - struct Iterator { - bool valid; - - const TKey *key; - TValue *value = nullptr; - - private: - uint32_t pos; - friend class OAHashMap; - }; - - Iterator iter() const { - Iterator it; - - it.valid = true; - it.pos = 0; - - return next_iter(it); - } - - Iterator next_iter(const Iterator &p_iter) const { - if (!p_iter.valid) { - return p_iter; - } - - Iterator it; - it.valid = false; - it.pos = p_iter.pos; - it.key = nullptr; - it.value = nullptr; - - for (uint32_t i = it.pos; i < capacity; i++) { - it.pos = i + 1; - - if (hashes[i] == EMPTY_HASH) { - continue; - } - - it.valid = true; - it.key = &keys[i]; - it.value = &values[i]; - return it; - } - - return it; - } - - OAHashMap(std::initializer_list> p_init) { - reserve(p_init.size()); - for (const KeyValue &E : p_init) { - set(E.key, E.value); - } - } - - OAHashMap(const OAHashMap &p_other) { - (*this) = p_other; - } - - void operator=(const OAHashMap &p_other) { - if (capacity != 0) { - clear(); - } - - _resize_and_rehash(p_other.capacity); - - for (Iterator it = p_other.iter(); it.valid; it = p_other.next_iter(it)) { - set(*it.key, *it.value); - } - } - - OAHashMap(uint32_t p_initial_capacity = 64) { - // Capacity can't be 0. - capacity = MAX(1u, p_initial_capacity); - - keys = static_cast(Memory::alloc_static(sizeof(TKey) * capacity)); - values = static_cast(Memory::alloc_static(sizeof(TValue) * capacity)); - static_assert(EMPTY_HASH == 0, "Assuming EMPTY_HASH = 0 for alloc_static_zeroed call"); - hashes = static_cast(Memory::alloc_static_zeroed(sizeof(uint32_t) * capacity)); - } - - ~OAHashMap() { - for (uint32_t i = 0; i < capacity; i++) { - if (hashes[i] == EMPTY_HASH) { - continue; - } - - values[i].~TValue(); - keys[i].~TKey(); - } - - Memory::free_static(keys); - Memory::free_static(values); - Memory::free_static(hashes); - } -}; diff --git a/core/variant/variant_call.cpp b/core/variant/variant_call.cpp index 1ad69b4afb8..a370c0ca6ed 100644 --- a/core/variant/variant_call.cpp +++ b/core/variant/variant_call.cpp @@ -36,8 +36,8 @@ #include "core/io/marshalls.h" #include "core/object/class_db.h" #include "core/os/os.h" +#include "core/templates/a_hash_map.h" #include "core/templates/local_vector.h" -#include "core/templates/oa_hash_map.h" typedef void (*VariantFunc)(Variant &r_ret, Variant &p_self, const Variant **p_args); typedef void (*VariantConstructFunc)(Variant &r_ret, const Variant **p_args); @@ -1264,7 +1264,7 @@ struct VariantBuiltInMethodInfo { } }; -typedef OAHashMap BuiltinMethodMap; +typedef AHashMap BuiltinMethodMap; static BuiltinMethodMap *builtin_method_info; static List *builtin_method_names; @@ -1318,7 +1318,7 @@ void Variant::callp(const StringName &p_method, const Variant **p_args, int p_ar } else { r_error.error = Callable::CallError::CALL_OK; - const VariantBuiltInMethodInfo *imf = builtin_method_info[type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *imf = builtin_method_info[type].getptr(p_method); if (!imf) { r_error.error = Callable::CallError::CALL_ERROR_INVALID_METHOD; @@ -1350,7 +1350,7 @@ void Variant::call_const(const StringName &p_method, const Variant **p_args, int } else { r_error.error = Callable::CallError::CALL_OK; - const VariantBuiltInMethodInfo *imf = builtin_method_info[type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *imf = builtin_method_info[type].getptr(p_method); if (!imf) { r_error.error = Callable::CallError::CALL_ERROR_INVALID_METHOD; @@ -1369,7 +1369,7 @@ void Variant::call_const(const StringName &p_method, const Variant **p_args, int void Variant::call_static(Variant::Type p_type, const StringName &p_method, const Variant **p_args, int p_argcount, Variant &r_ret, Callable::CallError &r_error) { r_error.error = Callable::CallError::CALL_OK; - const VariantBuiltInMethodInfo *imf = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *imf = builtin_method_info[p_type].getptr(p_method); if (!imf) { r_error.error = Callable::CallError::CALL_ERROR_INVALID_METHOD; @@ -1404,35 +1404,35 @@ bool Variant::has_builtin_method(Variant::Type p_type, const StringName &p_metho Variant::ValidatedBuiltInMethod Variant::get_validated_builtin_method(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, nullptr); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, nullptr); return method->validated_call; } Variant::PTRBuiltInMethod Variant::get_ptr_builtin_method(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, nullptr); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, nullptr); return method->ptrcall; } MethodInfo Variant::get_builtin_method_info(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, MethodInfo()); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, MethodInfo()); return method->get_method_info(p_method); } int Variant::get_builtin_method_argument_count(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, 0); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, 0); return method->argument_count; } Variant::Type Variant::get_builtin_method_argument_type(Variant::Type p_type, const StringName &p_method, int p_argument) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, Variant::NIL); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, Variant::NIL); ERR_FAIL_INDEX_V(p_argument, method->argument_count, Variant::NIL); return method->get_argument_type(p_argument); @@ -1440,7 +1440,7 @@ Variant::Type Variant::get_builtin_method_argument_type(Variant::Type p_type, co String Variant::get_builtin_method_argument_name(Variant::Type p_type, const StringName &p_method, int p_argument) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, String()); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, String()); #ifdef DEBUG_ENABLED ERR_FAIL_INDEX_V(p_argument, method->argument_count, String()); @@ -1452,14 +1452,14 @@ String Variant::get_builtin_method_argument_name(Variant::Type p_type, const Str Vector Variant::get_builtin_method_default_arguments(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, Vector()); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, Vector()); return method->default_arguments; } bool Variant::has_builtin_method_return_value(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, false); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, false); return method->has_return_type; } @@ -1478,35 +1478,35 @@ int Variant::get_builtin_method_count(Variant::Type p_type) { Variant::Type Variant::get_builtin_method_return_type(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, Variant::NIL); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, Variant::NIL); return method->return_type; } bool Variant::is_builtin_method_const(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, false); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, false); return method->is_const; } bool Variant::is_builtin_method_static(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, false); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, false); return method->is_static; } bool Variant::is_builtin_method_vararg(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, false); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, false); return method->is_vararg; } uint32_t Variant::get_builtin_method_hash(Variant::Type p_type, const StringName &p_method) { ERR_FAIL_INDEX_V(p_type, Variant::VARIANT_MAX, 0); - const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].lookup_ptr(p_method); + const VariantBuiltInMethodInfo *method = builtin_method_info[p_type].getptr(p_method); ERR_FAIL_NULL_V(method, 0); uint32_t hash = hash_murmur3_one_32(method->is_const); hash = hash_murmur3_one_32(method->is_static, hash); @@ -1531,7 +1531,7 @@ void Variant::get_method_list(List *p_list) const { } } else { for (const StringName &E : builtin_method_names[type]) { - const VariantBuiltInMethodInfo *method = builtin_method_info[type].lookup_ptr(E); + const VariantBuiltInMethodInfo *method = builtin_method_info[type].getptr(E); ERR_CONTINUE(!method); p_list->push_back(method->get_method_info(E)); } diff --git a/core/variant/variant_construct.h b/core/variant/variant_construct.h index c48d8eb1bec..2193982edf8 100644 --- a/core/variant/variant_construct.h +++ b/core/variant/variant_construct.h @@ -37,8 +37,8 @@ #include "core/io/compression.h" #include "core/object/class_db.h" #include "core/os/os.h" +#include "core/templates/a_hash_map.h" #include "core/templates/local_vector.h" -#include "core/templates/oa_hash_map.h" template struct PtrConstruct {}; diff --git a/core/variant/variant_utility.cpp b/core/variant/variant_utility.cpp index 239e3bce24b..cf7e2dcc765 100644 --- a/core/variant/variant_utility.cpp +++ b/core/variant/variant_utility.cpp @@ -34,7 +34,7 @@ #include "core/object/ref_counted.h" #include "core/object/script_language.h" #include "core/os/os.h" -#include "core/templates/oa_hash_map.h" +#include "core/templates/a_hash_map.h" #include "core/templates/rid.h" #include "core/templates/rid_owner.h" #include "core/variant/binder_common.h" @@ -1596,7 +1596,7 @@ struct VariantUtilityFunctionInfo { Variant::UtilityFunctionType type; }; -static OAHashMap utility_function_table; +static AHashMap utility_function_table; static List utility_function_name_table; template @@ -1788,7 +1788,7 @@ void Variant::_unregister_variant_utility_functions() { } void Variant::call_utility_function(const StringName &p_name, Variant *r_ret, const Variant **p_args, int p_argcount, Callable::CallError &r_error) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { r_error.error = Callable::CallError::CALL_ERROR_INVALID_METHOD; r_error.argument = 0; @@ -1816,7 +1816,7 @@ bool Variant::has_utility_function(const StringName &p_name) { } Variant::ValidatedUtilityFunction Variant::get_validated_utility_function(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return nullptr; } @@ -1825,7 +1825,7 @@ Variant::ValidatedUtilityFunction Variant::get_validated_utility_function(const } Variant::PTRUtilityFunction Variant::get_ptr_utility_function(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return nullptr; } @@ -1834,7 +1834,7 @@ Variant::PTRUtilityFunction Variant::get_ptr_utility_function(const StringName & } Variant::UtilityFunctionType Variant::get_utility_function_type(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return Variant::UTILITY_FUNC_TYPE_MATH; } @@ -1844,7 +1844,7 @@ Variant::UtilityFunctionType Variant::get_utility_function_type(const StringName MethodInfo Variant::get_utility_function_info(const StringName &p_name) { MethodInfo info; - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (bfi) { info.name = p_name; if (bfi->returns_value && bfi->return_type == Variant::NIL) { @@ -1865,7 +1865,7 @@ MethodInfo Variant::get_utility_function_info(const StringName &p_name) { } int Variant::get_utility_function_argument_count(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return 0; } @@ -1874,7 +1874,7 @@ int Variant::get_utility_function_argument_count(const StringName &p_name) { } Variant::Type Variant::get_utility_function_argument_type(const StringName &p_name, int p_arg) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return Variant::NIL; } @@ -1883,7 +1883,7 @@ Variant::Type Variant::get_utility_function_argument_type(const StringName &p_na } String Variant::get_utility_function_argument_name(const StringName &p_name, int p_arg) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return String(); } @@ -1893,7 +1893,7 @@ String Variant::get_utility_function_argument_name(const StringName &p_name, int } bool Variant::has_utility_function_return_value(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return false; } @@ -1901,7 +1901,7 @@ bool Variant::has_utility_function_return_value(const StringName &p_name) { } Variant::Type Variant::get_utility_function_return_type(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return Variant::NIL; } @@ -1910,7 +1910,7 @@ Variant::Type Variant::get_utility_function_return_type(const StringName &p_name } bool Variant::is_utility_function_vararg(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); if (!bfi) { return false; } @@ -1919,7 +1919,7 @@ bool Variant::is_utility_function_vararg(const StringName &p_name) { } uint32_t Variant::get_utility_function_hash(const StringName &p_name) { - const VariantUtilityFunctionInfo *bfi = utility_function_table.lookup_ptr(p_name); + const VariantUtilityFunctionInfo *bfi = utility_function_table.getptr(p_name); ERR_FAIL_NULL_V(bfi, 0); uint32_t hash = hash_murmur3_one_32(bfi->is_vararg); diff --git a/drivers/gles3/shader_gles3.cpp b/drivers/gles3/shader_gles3.cpp index 0fd25a61f86..02443b00027 100644 --- a/drivers/gles3/shader_gles3.cpp +++ b/drivers/gles3/shader_gles3.cpp @@ -570,10 +570,10 @@ bool ShaderGLES3::_load_from_cache(Version *p_version) { int cache_variant_count = static_cast(f->get_32()); ERR_FAIL_COND_V_MSG(cache_variant_count != variant_count, false, "shader cache variant count mismatch, expected " + itos(variant_count) + " got " + itos(cache_variant_count)); //should not happen but check - LocalVector> variants; + LocalVector> variants; for (int i = 0; i < cache_variant_count; i++) { uint32_t cache_specialization_count = f->get_32(); - OAHashMap variant; + AHashMap variant; for (uint32_t j = 0; j < cache_specialization_count; j++) { uint64_t specialization_key = f->get_64(); uint32_t variant_size = f->get_32(); @@ -648,18 +648,14 @@ void ShaderGLES3::_save_to_cache(Version *p_version) { f->store_32(variant_count); for (int i = 0; i < variant_count; i++) { - int cache_specialization_count = p_version->variants[i].get_num_elements(); + int cache_specialization_count = p_version->variants[i].size(); f->store_32(cache_specialization_count); - for (OAHashMap::Iterator it = p_version->variants[i].iter(); it.valid; it = p_version->variants[i].next_iter(it)) { - const uint64_t specialization_key = *it.key; + for (KeyValue &kv : p_version->variants[i]) { + const uint64_t specialization_key = kv.key; f->store_64(specialization_key); - const Version::Specialization *specialization = it.value; - if (specialization == nullptr) { - f->store_32(0); - continue; - } + const Version::Specialization *specialization = &kv.value; GLint program_size = 0; glGetProgramiv(specialization->id, GL_PROGRAM_BINARY_LENGTH, &program_size); if (program_size == 0) { @@ -689,11 +685,11 @@ void ShaderGLES3::_clear_version(Version *p_version) { } for (int i = 0; i < variant_count; i++) { - for (OAHashMap::Iterator it = p_version->variants[i].iter(); it.valid; it = p_version->variants[i].next_iter(it)) { - if (it.value->id != 0) { - glDeleteShader(it.value->vert_id); - glDeleteShader(it.value->frag_id); - glDeleteProgram(it.value->id); + for (KeyValue &kv : p_version->variants[i]) { + if (kv.value.id != 0) { + glDeleteShader(kv.value.vert_id); + glDeleteShader(kv.value.frag_id); + glDeleteProgram(kv.value.id); } } } @@ -709,7 +705,7 @@ void ShaderGLES3::_initialize_version(Version *p_version) { } p_version->variants.reserve(variant_count); for (int i = 0; i < variant_count; i++) { - OAHashMap variant; + AHashMap variant; p_version->variants.push_back(variant); Version::Specialization spec; _compile_specialization(spec, i, p_version, specialization_default_mask); diff --git a/drivers/gles3/shader_gles3.h b/drivers/gles3/shader_gles3.h index bfa2ebb4531..fcee94bc444 100644 --- a/drivers/gles3/shader_gles3.h +++ b/drivers/gles3/shader_gles3.h @@ -102,7 +102,7 @@ private: } }; - LocalVector> variants; + LocalVector> variants; }; Mutex variant_set_mutex; @@ -192,25 +192,25 @@ protected: _initialize_version(version); //may lack initialization } - Version::Specialization *spec = version->variants[p_variant].lookup_ptr(p_specialization); + Version::Specialization *spec = version->variants[p_variant].getptr(p_specialization); if (!spec) { if (false) { // Queue load this specialization and use defaults in the meantime (TODO) - spec = version->variants[p_variant].lookup_ptr(specialization_default_mask); + spec = version->variants[p_variant].getptr(specialization_default_mask); } else { // Compile on the spot Version::Specialization s; _compile_specialization(s, p_variant, version, p_specialization); version->variants[p_variant].insert(p_specialization, s); - spec = version->variants[p_variant].lookup_ptr(p_specialization); + spec = version->variants[p_variant].getptr(p_specialization); if (shader_cache_dir_valid) { _save_to_cache(version); } } } else if (spec->build_queued) { // Still queued, wait - spec = version->variants[p_variant].lookup_ptr(specialization_default_mask); + spec = version->variants[p_variant].getptr(specialization_default_mask); } if (!spec || !spec->ok) { @@ -228,7 +228,7 @@ protected: Version *version = version_owner.get_or_null(p_version); ERR_FAIL_NULL_V(version, -1); ERR_FAIL_INDEX_V(p_variant, int(version->variants.size()), -1); - Version::Specialization *spec = version->variants[p_variant].lookup_ptr(p_specialization); + Version::Specialization *spec = version->variants[p_variant].getptr(p_specialization); ERR_FAIL_NULL_V(spec, -1); ERR_FAIL_INDEX_V(p_which, int(spec->uniform_location.size()), -1); return spec->uniform_location[p_which]; diff --git a/editor/gui/editor_quick_open_dialog.cpp b/editor/gui/editor_quick_open_dialog.cpp index f33ea093d80..a6d87005c04 100644 --- a/editor/gui/editor_quick_open_dialog.cpp +++ b/editor/gui/editor_quick_open_dialog.cpp @@ -475,7 +475,7 @@ void QuickOpenResultContainer::set_query_and_update(const String &p_query) { Vector *QuickOpenResultContainer::_get_history() { if (base_types.size() == 1) { - return selected_history.lookup_ptr(base_types[0]); + return selected_history.getptr(base_types[0]); } return nullptr; } @@ -485,7 +485,7 @@ void QuickOpenResultContainer::_setup_candidate(QuickOpenResultCandidate &p_cand p_candidate.result = nullptr; StringName actual_type; { - StringName *actual_type_ptr = filetypes.lookup_ptr(p_filepath); + StringName *actual_type_ptr = filetypes.getptr(p_filepath); if (actual_type_ptr) { actual_type = *actual_type_ptr; } else { @@ -496,12 +496,12 @@ void QuickOpenResultContainer::_setup_candidate(QuickOpenResultCandidate &p_cand if (item.preview.is_valid()) { p_candidate.thumbnail = item.preview; } else if (file_type_icons.has(actual_type)) { - p_candidate.thumbnail = *file_type_icons.lookup_ptr(actual_type); + p_candidate.thumbnail = *file_type_icons.getptr(actual_type); } else if (has_theme_icon(actual_type, EditorStringName(EditorIcons))) { p_candidate.thumbnail = get_editor_theme_icon(actual_type); file_type_icons.insert(actual_type, p_candidate.thumbnail); } else { - p_candidate.thumbnail = *file_type_icons.lookup_ptr(SNAME("__default_icon")); + p_candidate.thumbnail = *file_type_icons.getptr(SNAME("__default_icon")); } } @@ -820,11 +820,11 @@ void QuickOpenResultContainer::save_selected_item() { const StringName &base_type = base_types[0]; QuickOpenResultCandidate &selected = candidates.write[selection_index]; - Vector *type_history = selected_history.lookup_ptr(base_type); + Vector *type_history = selected_history.getptr(base_type); if (!type_history) { selected_history.insert(base_type, Vector()); - type_history = selected_history.lookup_ptr(base_type); + type_history = selected_history.getptr(base_type); } else { for (int i = 0; i < type_history->size(); i++) { if (selected.file_path == type_history->get(i).file_path) { diff --git a/editor/gui/editor_quick_open_dialog.h b/editor/gui/editor_quick_open_dialog.h index a730e7921fb..c0953e06f5d 100644 --- a/editor/gui/editor_quick_open_dialog.h +++ b/editor/gui/editor_quick_open_dialog.h @@ -30,7 +30,7 @@ #pragma once -#include "core/templates/oa_hash_map.h" +#include "core/templates/a_hash_map.h" #include "scene/gui/dialogs.h" #include "scene/gui/margin_container.h" @@ -111,10 +111,10 @@ private: Vector search_results; Vector base_types; Vector filepaths; - OAHashMap filetypes; + AHashMap filetypes; Vector candidates; - OAHashMap> selected_history; + AHashMap> selected_history; HashSet history_set; String query; @@ -142,7 +142,7 @@ private: CheckButton *include_addons_toggle = nullptr; CheckButton *fuzzy_search_toggle = nullptr; - OAHashMap> file_type_icons; + AHashMap> file_type_icons; static QuickOpenDisplayMode get_adaptive_display_mode(const Vector &p_base_types); diff --git a/modules/csg/csg_shape.cpp b/modules/csg/csg_shape.cpp index b6e65981249..7aa872bf85d 100644 --- a/modules/csg/csg_shape.cpp +++ b/modules/csg/csg_shape.cpp @@ -576,7 +576,7 @@ void CSGShape3D::update_shape() { CSGBrush *n = _get_brush(); ERR_FAIL_NULL_MSG(n, "Cannot get CSGBrush."); - OAHashMap vec_map; + AHashMap vec_map; Vector face_count; face_count.resize(n->materials.size() + 1); @@ -594,13 +594,12 @@ void CSGShape3D::update_shape() { for (int j = 0; j < 3; j++) { Vector3 v = n->faces[i].vertices[j]; - Vector3 add; - if (vec_map.lookup(v, add)) { - add += p.normal; + Vector3 *vec = vec_map.getptr(v); + if (vec) { + *vec += p.normal; } else { - add = p.normal; + vec_map.insert(v, p.normal); } - vec_map.set(v, add); } } @@ -655,8 +654,11 @@ void CSGShape3D::update_shape() { Vector3 normal = p.normal; - if (n->faces[i].smooth && vec_map.lookup(v, normal)) { - normal.normalize(); + if (n->faces[i].smooth) { + Vector3 *ptr = vec_map.getptr(v); + if (ptr) { + normal = ptr->normalized(); + } } if (n->faces[i].invert) { diff --git a/modules/gdscript/gdscript_utility_functions.cpp b/modules/gdscript/gdscript_utility_functions.cpp index 645400f07c1..56747d9eb0b 100644 --- a/modules/gdscript/gdscript_utility_functions.cpp +++ b/modules/gdscript/gdscript_utility_functions.cpp @@ -35,7 +35,7 @@ #include "core/io/resource_loader.h" #include "core/object/class_db.h" #include "core/object/object.h" -#include "core/templates/oa_hash_map.h" +#include "core/templates/a_hash_map.h" #include "core/templates/vector.h" #include "core/variant/typed_array.h" @@ -514,7 +514,7 @@ struct GDScriptUtilityFunctionInfo { bool is_constant = false; }; -static OAHashMap utility_function_table; +static AHashMap utility_function_table; static List utility_function_name_table; static void _register_function(const StringName &p_name, const MethodInfo &p_method_info, GDScriptUtilityFunctions::FunctionPtr p_function, bool p_is_const) { @@ -598,50 +598,50 @@ void GDScriptUtilityFunctions::unregister_functions() { } GDScriptUtilityFunctions::FunctionPtr GDScriptUtilityFunctions::get_function(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, nullptr); return info->function; } bool GDScriptUtilityFunctions::has_function_return_value(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, false); return info->info.return_val.type != Variant::NIL || bool(info->info.return_val.usage & PROPERTY_USAGE_NIL_IS_VARIANT); } Variant::Type GDScriptUtilityFunctions::get_function_return_type(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, Variant::NIL); return info->info.return_val.type; } StringName GDScriptUtilityFunctions::get_function_return_class(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, StringName()); return info->info.return_val.class_name; } Variant::Type GDScriptUtilityFunctions::get_function_argument_type(const StringName &p_function, int p_arg) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, Variant::NIL); ERR_FAIL_INDEX_V(p_arg, info->info.arguments.size(), Variant::NIL); return info->info.arguments[p_arg].type; } int GDScriptUtilityFunctions::get_function_argument_count(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, 0); return info->info.arguments.size(); } bool GDScriptUtilityFunctions::is_function_vararg(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, false); return (bool)(info->info.flags & METHOD_FLAG_VARARG); } bool GDScriptUtilityFunctions::is_function_constant(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, false); return info->is_constant; } @@ -657,7 +657,7 @@ void GDScriptUtilityFunctions::get_function_list(List *r_functions) } MethodInfo GDScriptUtilityFunctions::get_function_info(const StringName &p_function) { - GDScriptUtilityFunctionInfo *info = utility_function_table.lookup_ptr(p_function); + GDScriptUtilityFunctionInfo *info = utility_function_table.getptr(p_function); ERR_FAIL_NULL_V(info, MethodInfo()); return info->info; } diff --git a/tests/core/templates/test_oa_hash_map.h b/tests/core/templates/test_oa_hash_map.h deleted file mode 100644 index 2bc368649d4..00000000000 --- a/tests/core/templates/test_oa_hash_map.h +++ /dev/null @@ -1,248 +0,0 @@ -/**************************************************************************/ -/* test_oa_hash_map.h */ -/**************************************************************************/ -/* This file is part of: */ -/* GODOT ENGINE */ -/* https://godotengine.org */ -/**************************************************************************/ -/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */ -/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */ -/* */ -/* Permission is hereby granted, free of charge, to any person obtaining */ -/* a copy of this software and associated documentation files (the */ -/* "Software"), to deal in the Software without restriction, including */ -/* without limitation the rights to use, copy, modify, merge, publish, */ -/* distribute, sublicense, and/or sell copies of the Software, and to */ -/* permit persons to whom the Software is furnished to do so, subject to */ -/* the following conditions: */ -/* */ -/* The above copyright notice and this permission notice shall be */ -/* included in all copies or substantial portions of the Software. */ -/* */ -/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ -/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ -/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */ -/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ -/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ -/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ -/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ -/**************************************************************************/ - -#pragma once - -#include "core/templates/oa_hash_map.h" -#include "scene/resources/texture.h" - -#include "tests/test_macros.h" - -namespace TestOAHashMap { - -TEST_CASE("[OAHashMap] List initialization") { - OAHashMap map{ { 0, "A" }, { 1, "B" }, { 2, "C" }, { 3, "D" }, { 4, "E" } }; - - CHECK(map.get_num_elements() == 5); - String value; - CHECK(map.lookup(0, value)); - CHECK(value == "A"); - CHECK(map.lookup(1, value)); - CHECK(value == "B"); - CHECK(map.lookup(2, value)); - CHECK(value == "C"); - CHECK(map.lookup(3, value)); - CHECK(value == "D"); - CHECK(map.lookup(4, value)); - CHECK(value == "E"); -} - -TEST_CASE("[OAHashMap] List initialization with existing elements") { - OAHashMap map{ { 0, "A" }, { 0, "B" }, { 0, "C" }, { 0, "D" }, { 0, "E" } }; - - CHECK(map.get_num_elements() == 1); - String value; - CHECK(map.lookup(0, value)); - CHECK(value == "E"); -} - -TEST_CASE("[OAHashMap] Insert element") { - OAHashMap map; - map.insert(42, 84); - int data = 0; - bool lookup_res = map.lookup(42, data); - int value = *map.lookup_ptr(42); - CHECK(lookup_res); - CHECK(value == 84); - CHECK(data == 84); -} - -TEST_CASE("[OAHashMap] Set element") { - OAHashMap map; - map.set(42, 84); - int data = 0; - bool lookup_res = map.lookup(42, data); - int value = *map.lookup_ptr(42); - CHECK(lookup_res); - CHECK(value == 84); - CHECK(data == 84); -} - -TEST_CASE("[OAHashMap] Overwrite element") { - OAHashMap map; - map.set(42, 84); - map.set(42, 1234); - int result = *map.lookup_ptr(42); - CHECK(result == 1234); -} - -TEST_CASE("[OAHashMap] Remove element") { - OAHashMap map; - map.insert(42, 84); - map.remove(42); - CHECK(!map.has(42)); -} - -TEST_CASE("[OAHashMap] Get Num_Elements") { - OAHashMap map; - map.set(42, 84); - map.set(123, 84); - map.set(123, 84); - map.set(0, 84); - map.set(123485, 84); - - CHECK(map.get_num_elements() == 4); -} - -TEST_CASE("[OAHashMap] Iteration") { - OAHashMap map; - map.insert(42, 84); - map.insert(123, 12385); - map.insert(0, 12934); - map.insert(123485, 1238888); - map.set(123, 111111); - - Vector> expected; - expected.push_back(Pair(42, 84)); - expected.push_back(Pair(123, 111111)); - expected.push_back(Pair(0, 12934)); - expected.push_back(Pair(123485, 1238888)); - - for (OAHashMap::Iterator it = map.iter(); it.valid; it = map.next_iter(it)) { - int64_t result = expected.find(Pair(*it.key, *it.value)); - CHECK(result >= 0); - } -} - -TEST_CASE("[OAHashMap] Insert, iterate, remove many strings") { - uint64_t pre_mem = Memory::get_mem_usage(); - { - const int elem_max = 40; - OAHashMap map; - for (int i = 0; i < elem_max; i++) { - map.insert(itos(i), i); - } - - Vector elems_still_valid; - - for (int i = 0; i < elem_max; i++) { - if ((i % 5) == 0) { - map.remove(itos(i)); - } else { - elems_still_valid.push_back(itos(i)); - } - } - - CHECK(elems_still_valid.size() == map.get_num_elements()); - - for (int i = 0; i < elems_still_valid.size(); i++) { - CHECK(map.has(elems_still_valid[i])); - } - } - - CHECK(Memory::get_mem_usage() == pre_mem); -} - -TEST_CASE("[OAHashMap] Clear") { - OAHashMap map; - map.insert(42, 84); - map.insert(0, 1234); - map.clear(); - CHECK(!map.has(42)); - CHECK(!map.has(0)); - CHECK(map.is_empty()); -} - -TEST_CASE("[OAHashMap] Copy constructor") { - uint64_t pre_mem = Memory::get_mem_usage(); - { - OAHashMap map0; - const uint32_t count = 5; - for (uint32_t i = 0; i < count; i++) { - map0.insert(i, i); - } - OAHashMap map1(map0); - CHECK(map0.get_num_elements() == map1.get_num_elements()); - CHECK(map0.get_capacity() == map1.get_capacity()); - CHECK(*map0.lookup_ptr(0) == *map1.lookup_ptr(0)); - } - CHECK(Memory::get_mem_usage() == pre_mem); -} - -TEST_CASE("[OAHashMap] Operator =") { - uint64_t pre_mem = Memory::get_mem_usage(); - { - OAHashMap map0; - OAHashMap map1; - const uint32_t count = 5; - map1.insert(1234, 1234); - for (uint32_t i = 0; i < count; i++) { - map0.insert(i, i); - } - map1 = map0; - CHECK(map0.get_num_elements() == map1.get_num_elements()); - CHECK(map0.get_capacity() == map1.get_capacity()); - CHECK(*map0.lookup_ptr(0) == *map1.lookup_ptr(0)); - } - CHECK(Memory::get_mem_usage() == pre_mem); -} - -TEST_CASE("[OAHashMap] Non-trivial types") { - uint64_t pre_mem = Memory::get_mem_usage(); - { - OAHashMap> map1; - const uint32_t count = 10; - for (uint32_t i = 0; i < count; i++) { - String string = "qwerty"; - string += itos(i); - Ref ref_texture_2d; - - map1.set(string, ref_texture_2d); - Ref map_vec = *map1.lookup_ptr(string); - CHECK(map_vec == ref_texture_2d); - } - OAHashMap> map1copy(map1); - CHECK(map1copy.has(String("qwerty0"))); - map1copy = map1; - CHECK(map1copy.has(String("qwerty2"))); - - OAHashMap map2; - - for (uint32_t i = 0; i < count; i++) { - Vector4 *vec = memnew(Vector4); - vec->x = 10; - vec->y = 12; - vec->z = 151; - vec->w = -13; - map2.set(i, vec); - Vector4 *p = nullptr; - map2.lookup(i, p); - CHECK(*p == *vec); - } - - OAHashMap map3(map2); - for (OAHashMap::Iterator it = map2.iter(); it.valid; it = map2.next_iter(it)) { - memdelete(*(it.value)); - } - } - CHECK(Memory::get_mem_usage() == pre_mem); -} - -} // namespace TestOAHashMap diff --git a/tests/test_main.cpp b/tests/test_main.cpp index 44d36a00eff..994958b4da5 100644 --- a/tests/test_main.cpp +++ b/tests/test_main.cpp @@ -103,7 +103,6 @@ #include "tests/core/templates/test_list.h" #include "tests/core/templates/test_local_vector.h" #include "tests/core/templates/test_lru.h" -#include "tests/core/templates/test_oa_hash_map.h" #include "tests/core/templates/test_paged_array.h" #include "tests/core/templates/test_rid.h" #include "tests/core/templates/test_span.h"