#include #include #include #include #include #include #include namespace ecs { namespace entity { using id = size_t; using entities = std::vector; } namespace component { using name = std::string; using is_male = bool; using detail = std::pair; using detail_component = std::pair; enum class type { algue, Mérou, Thon, PoissonClown, Sole, Bar, Carpe }; using type_component = std::pair; } namespace system { using details = std::vector; using types = std::vector; } namespace internal { entity::entities _entities; system::details _details; system::types _types; } bool is_algue(component::type t) { return (t == component::type::algue); } bool is_poisson(component::type t) { return !is_algue(t); } bool is_carnivore(component::type t) { return (t == component::type::Mérou || t == component::type::Thon || t == component::type::PoissonClown); } bool is_herbivore(component::type t) { return (t == component::type::Sole || t == component::type::Bar || t == component::type::Carpe); } std::string to_string(component::type t) { static const std::string types[] = { "Algue", "Mérou", "Thon", "Poisson-clown", "Sole", "Bar", "Carpe" }; const auto i = static_cast(t); return types[i]; } entity::id create_entity() { const auto id = internal::_entities.empty() ? 1 : internal::_entities.back() + 1; internal::_entities.push_back(id); return id; } entity::id add_algue() { const auto id = create_entity(); internal::_types.push_back(std::make_pair(id, component::type::algue)); return id; } entity::id add_poisson(component::type t, component::name n, component::is_male m) { assert(is_poisson(t)); const auto id = create_entity(); internal::_types.push_back(std::make_pair(id, t)); internal::_details.push_back(std::make_pair(id, make_pair(n, m))); return id; } void remove_entity(entity::id id) { const auto entities_it = std::remove(internal::_entities.begin(), internal::_entities.end(), id); internal::_entities.erase(entities_it, internal::_entities.end()); const auto details_it = std::remove_if(internal::_details.begin(), internal::_details.end(), [id](auto p){ return (p.first == id); }); internal::_details.erase(details_it, internal::_details.end()); const auto types_it = std::remove_if(internal::_types.begin(), internal::_types.end(), [id](auto p){ return (p.first == id); }); internal::_types.erase(types_it, internal::_types.end()); } void eat(entity::id eater, entity::id target) { assert(eater != target); const auto eater_it = std::find_if(begin(internal::_types), end(internal::_types), [eater](auto p){ return (p.first == eater); }); const auto target_it = std::find_if(begin(internal::_types), end(internal::_types), [target](auto p){ return (p.first == target); }); assert(is_poisson(eater_it->second)); assert(is_carnivore(eater_it->second) || (is_herbivore(eater_it->second) && is_algue(target_it->second))); remove_entity(target); //eat } void print_algues() { const auto count = std::count_if(begin(internal::_types), end(internal::_types), [](auto p){ return (p.second == component::type::algue); }); std::cout << "algues: " << count; } void print_poissons() { if (internal::_details.empty()) { std::cout << "No poissons"; return; } std::cout << internal::_details.size() << " poissons: "; auto print = [](auto p){ return (p.second.first + " [" + (p.second.second ? 'M' : 'F') + ']'); }; std::transform(begin(internal::_details), end(internal::_details) - 1, std::ostream_iterator(std::cout, ", "), print); std::cout << print(internal::_details.back()); } void print() { print_algues(); std::cout << ". "; print_poissons(); std::cout << '.' << std::endl; } } int main() { ecs::add_algue(); ecs::add_algue(); ecs::add_algue(); ecs::add_algue(); ecs::add_algue(); ecs::add_algue(); ecs::add_algue(); const auto algue = ecs::add_algue(); const auto carnivore = ecs::add_poisson(ecs::component::type::Mérou, "toto", true); const auto poisson = ecs::add_poisson(ecs::component::type::Mérou, "titi", false); const auto herbivore = ecs::add_poisson(ecs::component::type::Mérou, "tata", true); ecs::add_poisson(ecs::component::type::Mérou, "tuto", false); ecs::add_poisson(ecs::component::type::Mérou, "tyty", true); ecs::print(); ecs::remove_entity(poisson); ecs::print(); ecs::eat(herbivore, algue); ecs::eat(carnivore, herbivore); ecs::print(); return 0; }