void Person::RequestFloor(Environment &env) { Floor *next = path_.front(); if (!next) { std::ostringstream oss("Invalid operation: no next floor in path ", std::ostringstream::ate); oss << "ID of person: <" << GetId(); oss << ", this error should never occur."; throw std::runtime_error(oss.str()); } for (int i = 0; i < elevator_->GetInterfaceCount(); ++i) { Interface *interf = elevator_->GetInterface(i); Floor *floor = static_cast<Floor*>(interf->GetLoadable(0)); if (floor == next) { action_ = env.SendEvent("Interface::Interact", 3, this, elevator_->GetInterface(i)); return; } } std::ostringstream oss("Invalid operation: ", std::ostringstream::ate); oss << elevator_->GetName() << " can not go to Floor " << next->GetId(); oss << ", this error should never occur."; throw std::runtime_error(oss.str()); }
void Person::RequestElevator(Environment &env, int time) { if (current_ == final_) return; Floor *next = path_.front(); if (!next) { std::ostringstream oss("Invalid operation: no next floor in path ", std::ostringstream::ate); oss << "ID of person: <" << GetId(); oss << ", this error should never occur."; throw std::runtime_error(oss.str()); } for (int i = 0; i < current_->GetInterfaceCount(); ++i) { Interface *interf = current_->GetInterface(i); Elevator *ele = static_cast<Elevator*>(interf->GetLoadable(0)); if (ele->HasFloor(next)) { requested_ = current_->GetInterface(i); env.SendEvent("Interface::Interact", time - env.GetClock(), this, requested_); return; } } std::ostringstream oss("Invalid operation: no elevator available to go from Floor ", std::ostringstream::ate); oss << current_->GetId() << " to Floor " << next->GetId(); oss << ", this error should never occur."; throw std::runtime_error(oss.str()); }
void Elevator::Validate() { Entity::Validate(); if (speed_ <= 0) { std::ostringstream oss("Speed of ", std::ostringstream::ate); oss << GetName() << " must be positive."; throw TestfileException(oss.str()); } if (load_ < 10) { std::ostringstream oss("Maximum load of ", std::ostringstream::ate); oss << GetName() << " must be greater or equal to 10."; throw TestfileException(oss.str()); } if (!current_) { std::ostringstream oss("Starting floor of ", std::ostringstream::ate); oss << GetName() << " is null."; throw TestfileException(oss.str()); } if (current_->GetType() != "Floor") { std::ostringstream oss("Starting floor of ", std::ostringstream::ate); oss << GetName() << " does not reference a floor object."; throw TestfileException(oss.str()); } if (count_ < 2) { std::ostringstream oss("", std::ostringstream::ate); oss << GetName() << " must have at least 2 interfaces."; throw TestfileException(oss.str()); } std::set<Interface*> unique; Floor *lowest = nullptr; Floor *highest = nullptr; for (int i = 0; i < count_; ++i) { Interface *interf = interfs_[i]; if (!interf) { std::ostringstream oss("An interface of ", std::ostringstream::ate); oss << GetName() << " is null."; throw TestfileException(oss.str()); } if (unique.count(interf)) { std::ostringstream oss("Interfaces used by ", std::ostringstream::ate); oss << GetName() << " are not unique."; throw TestfileException(oss.str()); } unique.insert(interf); if (interf->GetType() != "Interface") { std::ostringstream oss("Interface ", std::ostringstream::ate); oss << interf->GetId() << " of "; oss << GetName() << " is not an interface object."; throw TestfileException(oss.str()); } if (interf->GetLoadableCount() != 1) { std::ostringstream oss("", std::ostringstream::ate); oss << interf->GetName() << " of "; oss << GetName() << " must reference exactly one object."; throw TestfileException(oss.str()); } Loadable *loadable = interf->GetLoadable(0); if (!loadable) { std::ostringstream oss("Referenced object of ", std::ostringstream::ate); oss << interf->GetName() << " of "; oss << GetName() << " is null."; throw TestfileException(oss.str()); } if (loadable->GetType() != "Floor") { std::ostringstream oss("Referenced object of ", std::ostringstream::ate); oss << interf->GetName() << " of "; oss << GetName() << " must be an floor object."; throw TestfileException(oss.str()); } Floor *floor = static_cast<Floor*>(loadable); if (!floor->HasElevator(this)) { std::ostringstream oss("Floor ", std::ostringstream::ate); oss << floor->GetId() << " referenced by "; oss << interf->GetName() << " of "; oss << GetName() << " does not point back to the elevator."; throw TestfileException(oss.str()); } if (!lowest) lowest = floor; else if (lowest->IsBelow(floor)) { lowest = floor; } if (!highest) highest = floor; else if (highest->IsAbove(floor)) { highest = floor; } } if (highest->IsAbove(current_) || lowest->IsBelow(current_)) { std::ostringstream oss("Starting floor of ", std::ostringstream::ate); oss << GetName() << " is not between Floor " << lowest->GetId() << " and Floor " << highest->GetId() << "."; throw TestfileException(oss.str()); } // validate if the elevator can start in the starting floor if (!HasFloor(this->current_)) { std::ostringstream oss("Elevator ", std::ostringstream::ate); oss << GetId() << " can not start in Floor " << current_->GetId() << " because the Floor has no interface to this Elevator."; throw TestfileException(oss.str()); } Floor* floorTmp = CanReachFloor(lowest, highest); if (floorTmp) { std::ostringstream oss("Elevator ", std::ostringstream::ate); oss << GetId() << " can not reach center of Floor " << floorTmp->GetId() << "."; throw TestfileException(oss.str()); } }