From a557458977abe907fec3f241071f339a1999012d Mon Sep 17 00:00:00 2001 From: Alec Thomas Date: Thu, 29 Aug 2013 16:14:19 -0400 Subject: Speed up iteration a bit. --- entityx/Benchmarks_test.cc | 3 ++- entityx/Entity.h | 43 +++++++++++++++++----------------------- entityx/Entity_test.cc | 46 +++++++++++++++++++++---------------------- entityx/python/PythonSystem.h | 8 ++++---- 4 files changed, 47 insertions(+), 53 deletions(-) diff --git a/entityx/Benchmarks_test.cc b/entityx/Benchmarks_test.cc index c70deb9..d02896a 100644 --- a/entityx/Benchmarks_test.cc +++ b/entityx/Benchmarks_test.cc @@ -76,7 +76,7 @@ TEST_F(BenchmarksTest, TestDestroyEntitiesWithListener) { boost::timer::auto_cpu_timer t; cout << "destroying " << count << " entities" << endl; - for (auto e : entities) { + for (auto &e : entities) { e.destroy(); } } @@ -99,6 +99,7 @@ TEST_F(BenchmarksTest, TestEntityIteration) { for (int i = 0; i < 10; ++i) { for (auto e : em->entities_with_components()) { entityx::shared_ptr position = e.component(); + position.get(); } } } diff --git a/entityx/Entity.h b/entityx/Entity.h index 535b395..8eee892 100644 --- a/entityx/Entity.h +++ b/entityx/Entity.h @@ -69,6 +69,9 @@ public: static const Id INVALID; Entity() {} + Entity(const Entity &) = default; + Entity(Entity &&) = default; + Entity &operator = (const Entity &) = default; /** * Check if Entity handle is invalid. @@ -258,45 +261,39 @@ class EntityManager : public entityx::enable_shared_from_this, bo } bool operator == (const Iterator& rhs) const { return i_ == rhs.i_; } bool operator != (const Iterator& rhs) const { return i_ != rhs.i_; } - Entity operator * () { return Entity(manager_, manager_->create_id(i_)); } - const Entity operator * () const { return Entity(manager_, manager_->create_id(i_)); } + Entity operator * () { return Entity(view_.manager_, view_.manager_->create_id(i_)); } + const Entity operator * () const { return Entity(view_.manager_, view_.manager_->create_id(i_)); } private: friend class View; - Iterator() {} - - Iterator(entityx::shared_ptr manager, const std::vector &predicates, - const std::vector> &unpackers, uint32_t index) - : manager_(manager), predicates_(predicates), unpackers_(unpackers), i_(index) { + Iterator(const View &view, uint32_t index) : view_(view), i_(index) { next(); } void next() { - while (i_ < manager_->capacity() && !predicate()) { + while (i_ < view_.manager_->capacity() && !predicate()) { ++i_; } - if (i_ < manager_->capacity() && !unpackers_.empty()) { - Entity::Id id = manager_->create_id(i_); - for (auto unpacker : unpackers_) { + if (i_ < view_.manager_->capacity() && !view_.unpackers_.empty()) { + Entity::Id id = view_.manager_->create_id(i_); + for (auto &unpacker : view_.unpackers_) { unpacker(id); } } } bool predicate() { - Entity::Id id = manager_->create_id(i_); - for (auto &p : predicates_) { - if (!p(manager_, id)) { + Entity::Id id = view_.manager_->create_id(i_); + for (auto &p : view_.predicates_) { + if (!p(view_.manager_, id)) { return false; } } return true; } - entityx::shared_ptr manager_; - const std::vector predicates_; - std::vector> unpackers_; + const View &view_; uint32_t i_; }; @@ -305,18 +302,14 @@ class EntityManager : public entityx::enable_shared_from_this, bo predicates_.push_back(predicate); } - Iterator begin() { return Iterator(manager_, predicates_, unpackers_, 0); } - Iterator end() { return Iterator(manager_, predicates_, unpackers_, manager_->capacity()); } - const Iterator begin() const { return Iterator(manager_, predicates_, unpackers_, 0); } - const Iterator end() const { return Iterator(manager_, predicates_, unpackers_, manager_->size()); } + Iterator begin() { return Iterator(*this, 0); } + Iterator end() { return Iterator(*this, manager_->size()); } + const Iterator begin() const { return Iterator(*this, 0); } + const Iterator end() const { return Iterator(*this, manager_->size()); } template View &unpack_to(entityx::shared_ptr &a) { unpackers_.push_back(Unpacker(manager_, a)); - // This resulted in a segfault under clang 4.1 on OSX. No idea why. - // unpackers_.push_back([&a, this](uint32_t index) { - // a = manager_->component(Entity::Id(index, 0)); - // }); return *this; } diff --git a/entityx/Entity_test.cc b/entityx/Entity_test.cc index eaa2025..b779873 100644 --- a/entityx/Entity_test.cc +++ b/entityx/Entity_test.cc @@ -10,6 +10,7 @@ #include #include +#include #include #include #include "entityx/Entity.h" @@ -26,7 +27,7 @@ int size(const T &t) { int n = 0; for (auto i : t) { ++n; - (void)i; // Unused on purpose, suppress warning + (void)i; // Unused on purpose, suppress warning } return n; } @@ -74,33 +75,33 @@ class EntityManagerTest : public ::testing::Test { TEST_F(EntityManagerTest, TestCreateEntity) { - ASSERT_TRUE(em->size() == 0); + ASSERT_EQ(em->size(), 0UL); Entity e2; ASSERT_FALSE(e2.valid()); Entity e = em->create(); ASSERT_TRUE(e.valid()); - ASSERT_TRUE(em->size() == 1); + ASSERT_EQ(em->size(), 1UL); e2 = e; ASSERT_TRUE(e2.valid()); } TEST_F(EntityManagerTest, TestEntityAsBoolean) { - ASSERT_TRUE(em->size() == 0); + ASSERT_EQ(em->size(), 0UL); Entity e = em->create(); ASSERT_TRUE(e.valid()); - ASSERT_TRUE(em->size() == 1); + ASSERT_EQ(em->size(), 1UL); ASSERT_FALSE(!e); e.destroy(); - ASSERT_TRUE(em->size() == 0); + ASSERT_EQ(em->size(), 0UL); ASSERT_TRUE(!e); - Entity e2; // Not initialized + Entity e2; // Not initialized ASSERT_TRUE(!e2); } @@ -124,7 +125,7 @@ TEST_F(EntityManagerTest, TestEntityReuse) { TEST_F(EntityManagerTest, TestComponentConstruction) { auto e = em->create(); auto p = e.assign(1, 2); - //auto p = em->assign(e, 1, 2); + // auto p = em->assign(e, 1, 2); auto cp = e.component(); ASSERT_EQ(p, cp); ASSERT_FLOAT_EQ(1.0, cp->x); @@ -151,17 +152,17 @@ TEST_F(EntityManagerTest, TestDestroyEntity) { ASSERT_EQ(2, ep.use_count()); ASSERT_TRUE(e.valid()); ASSERT_TRUE(f.valid()); - ASSERT_TRUE(bool(e.component())); - ASSERT_TRUE(bool(e.component())); - ASSERT_TRUE(bool(f.component())); - ASSERT_TRUE(bool(f.component())); + ASSERT_TRUE(static_cast(e.component())); + ASSERT_TRUE(static_cast(e.component())); + ASSERT_TRUE(static_cast(f.component())); + ASSERT_TRUE(static_cast(f.component())); e.destroy(); ASSERT_FALSE(e.valid()); ASSERT_TRUE(f.valid()); - ASSERT_TRUE(bool(f.component())); - ASSERT_TRUE(bool(f.component())); + ASSERT_TRUE(static_cast(f.component())); + ASSERT_TRUE(static_cast(f.component())); ASSERT_EQ(1, ep.use_count()); } @@ -186,7 +187,6 @@ TEST_F(EntityManagerTest, TestGetEntitiesWithIntersectionOfComponents) { e.assign(); if (i % 3 == 0) e.assign(); - } ASSERT_EQ(50, size(em->entities_with_components())); ASSERT_EQ(75, size(em->entities_with_components())); @@ -212,8 +212,8 @@ TEST_F(EntityManagerTest, TestGetEntitiesWithComponentAndUnpacking) { entityx::shared_ptr direction; for (auto unused_entity : em->entities_with_components(position, direction)) { (void)unused_entity; - ASSERT_TRUE(bool(position)); - ASSERT_TRUE(bool(direction)); + ASSERT_TRUE(static_cast(position)); + ASSERT_TRUE(static_cast(direction)); auto pd = position_directions.at(i); ASSERT_EQ(position, pd.first); ASSERT_EQ(direction, pd.second); @@ -235,7 +235,7 @@ TEST_F(EntityManagerTest, TestUnpack) { } // gcc 4.7.2 does not allow this struct to be declared locally inside the TEST_F. -struct NullDeleter {template void operator()(T*) {} }; +struct NullDeleter {template void operator()(T *unused) {} }; TEST_F(EntityManagerTest, TestUnpackNullMissing) { Entity e = em->create(); @@ -292,14 +292,14 @@ TEST_F(EntityManagerTest, TestEntityDestroyedEvent) { for (auto e : entities) { e.destroy(); } - ASSERT_TRUE(entities == receiver.destroyed); + ASSERT_EQ(entities, receiver.destroyed); } TEST_F(EntityManagerTest, TestComponentAddedEvent) { struct ComponentAddedEventReceiver : public Receiver { void receive(const ComponentAddedEvent &event) { auto p = event.component; - float n = float(position_events); + float n = static_cast(position_events); ASSERT_EQ(p->x, n); ASSERT_EQ(p->y, n); position_events++; @@ -307,7 +307,7 @@ TEST_F(EntityManagerTest, TestComponentAddedEvent) { void receive(const ComponentAddedEvent &event) { auto p = event.component; - float n = float(direction_events); + float n = static_cast(direction_events); ASSERT_EQ(p->x, -n); ASSERT_EQ(p->y, -n); direction_events++; @@ -328,8 +328,8 @@ TEST_F(EntityManagerTest, TestComponentAddedEvent) { ASSERT_EQ(0, receiver.direction_events); for (int i = 0; i < 10; ++i) { Entity e = em->create(); - e.assign(float(i), float(i)); - e.assign(float(-i), float(-i)); + e.assign(static_cast(i), static_cast(i)); + e.assign(static_cast(-i), static_cast(-i)); } ASSERT_EQ(10, receiver.position_events); ASSERT_EQ(10, receiver.direction_events); diff --git a/entityx/python/PythonSystem.h b/entityx/python/PythonSystem.h index 1d2926b..b64e46c 100644 --- a/entityx/python/PythonSystem.h +++ b/entityx/python/PythonSystem.h @@ -80,7 +80,7 @@ public: /** * Create a new PythonComponent from an existing Python instance. */ - PythonComponent(boost::python::object object) : object(object) {} + explicit PythonComponent(boost::python::object object) : object(object) {} boost::python::object object; boost::python::list args; @@ -160,7 +160,7 @@ private: * A helper function for class_ to assign a component to an entity. */ template -void assign_to(entityx::shared_ptr component, Entity &entity) { +void assign_to(entityx::shared_ptr component, Entity &entity) { // NOLINT entity.assign(component); } @@ -170,7 +170,7 @@ void assign_to(entityx::shared_ptr component, Entity &entity) { * entity. */ template -entityx::shared_ptr get_component(Entity &entity) { +entityx::shared_ptr get_component(Entity &entity) { // NOLINT return entity.component(); } @@ -206,7 +206,7 @@ class PythonSystem : public entityx::System, public entityx::Recei public: typedef boost::function LoggerFunction; - PythonSystem(entityx::shared_ptr entity_manager); + PythonSystem(entityx::shared_ptr entity_manager); // NOLINT virtual ~PythonSystem(); /** -- cgit v1.2.3