FPType PASWithStep::getFlowShift() { FPType x[nbLinks_]; FPType y[nbLinks_]; int indexes[nbLinks_]; int size = 0; FPType dir[2]; dir[cheapSegm_] = expCost_ - cheapCost_; dir[1 - cheapSegm_] = -dir[cheapSegm_]; StarLink* link = NULL; int linkIndex = -1; for (int i = 0; i < 2; ++i) { for (std::list<StarLink*>::const_iterator it = segments_[i].begin(); it != segments_[i].end(); ++it) { link = *it; linkIndex = link->getIndex(); x[linkIndex] = link->getFlow(); y[linkIndex] = dir[i]; indexes[size] = linkIndex; ++size; } } (lineSearch_->getDerivative())->setDataPointers(size, x, y, indexes); return lineSearch_->execute(0.0, totalShift_ / dir[cheapSegm_]) * dir[cheapSegm_]; };
bool DAGraph::explore(int vertex, bool *visited){ visited[vertex] = true; preVisit(vertex); std::list<StarLink*> &linksList = (nodes_[vertex])->outLinks; int index = -1; bool backEdgeDetected = false; StarLink* link = NULL; for(std::list<StarLink*>::iterator it = linksList.begin(); it != linksList.end(); ++it){ link = *it; index = link->getNodeToIndex(); if (checkPositiveFlow(link->getIndex())) { handleExploredLink(link); if ((nodes_[index])->pre == 0) { backEdgeDetected = explore(index, visited); if (backEdgeDetected) return true; } if ((nodes_[index])->pre > 0 && (nodes_[index])->post == 0) { return handleBackEdge(link); } } } postVisit(vertex); return false; };
void Utils::getCommonLinks(PathBasedFlowMove *paths, std::list<StarLink*> &list, int nbLinks){ std::vector<int> indexes(nbLinks); std::vector<int> indexesTmp(nbLinks); std::vector<StarLink*> links(nbLinks); int size = 0; for (int i = 0; i < nbLinks; ++i) { indexes[i] = 0; indexesTmp[i] = 0; links[i] = NULL; } int index = -1; Path *path = NULL; int nbPaths = 0; for (PathAndDirection *pathDir = paths->beginPathDirection(); pathDir != NULL; pathDir = paths->getNextPathDirection()) { path = pathDir->getPath(); ++nbPaths; for(StarLinkIterator it = path->begin(); it != path->end(); ++it){ StarLink* link = *it; index = link->getIndex(); if (indexes[index] == 0) { indexesTmp[size] = index; ++size; links[index] = link; } ++indexes[index]; } } for (int i = 0; i < size; ++i) { index = indexesTmp[i]; if (indexes[index] == nbPaths) { list.push_back(links[index]); } } };
FPType Utils::checkFeasibility(StarNetwork *net, ODMatrix *mat){ std::vector<FPType> total(net->getNbNodes()); for (int i = 0; i < net->getNbNodes(); ++i) { total[i] = 0.0; } // load demands for (OriginIterator it = mat->begin(); it != mat->end(); ++it){ Origin* origin = *it; for (PairODIterator jt = origin->begin(); jt != origin->end(); ++jt) { PairOD* dest = *jt; total[origin->getIndex()] += dest->getDemand(); total[dest->getIndex()] -= dest->getDemand(); } } //travers network and check for (StarLink *link = net->beginOnlyLink(); link != NULL; link = net->getNextOnlyLink()) { total[link->getNodeFromIndex()] -= link->getFlow(); total[link->getNodeToIndex()] += link->getFlow(); } FPType maxVal = 0.0; for (int i = 0; i < net->getNbNodes(); ++i) { if (fabs(total[i]) > maxVal) maxVal = fabs(total[i]); } return maxVal; };
void Utils::getDisjointLinks(Path *path1, Path *path2, std::list<StarLink*> &list, int nbLinks){ std::vector<int> indexes(nbLinks); for (int i = 0; i < nbLinks; ++i) { indexes[i] = 0; } for (StarLinkIterator it = path1->begin(); it != path1->end(); ++it) { indexes[(*it)->getIndex()] = 1; } int index = -1; for (StarLinkIterator it = path2->begin(); it != path2->end(); ++it) { StarLink* link = *it; index = link->getIndex(); if (indexes[index] == 0) { list.push_back(link); } else { indexes[index] = -1; } } for (StarLinkIterator it = path1->begin(); it != path1->end(); ++it) { StarLink* link = *it; if (indexes[link->getIndex()] == 1) { list.push_back(link); } } assert(!list.empty()); };
int findLinkIndex(int tail, int head, StarNetwork* net, int guessIndex){ StarLink* link = net->getLink(guessIndex); assert(link != NULL); if (link->getNodeFrom() == tail && link->getNodeTo() == head) { return link->getIndex(); } return -1; };
FPType Utils::calculatePathDerivativeForDisjoint(const std::list<StarLink*> &list){ StarLink* link = NULL; FPType der = 0.0; for (std::list<StarLink*>::const_iterator it = list.begin(); it != list.end(); ++it) { link = *it; der += link->getDerivative(); } return der; };
FPType NonAdditivePC::calculate(Path *path, int odIndex) const{ assert(path != NULL && odIndex >=0); TollType totalToll = 0; FPType totalTime = 0.0; for (StarLinkIterator it = path->begin(); it != path->end(); ++it) { StarLink* link = *it; totalTime += link->getTime(); totalToll += tolls_[link->getIndex()]; } return calculate(totalTime, totalToll, odIndex); };
void assignRndTolls(ShortestPath* shPath, int destIndex, TollContainerType& tolls, FPType probabylity, TollType maxToll){ StarLink *link = shPath->getInComeLink(destIndex); int nextDest = link->getNodeFromIndex(); int linkIndex = -1; while (link != NULL) { linkIndex = link->getIndex(); tolls[linkIndex] = getRndNumberWithProbability(tolls[linkIndex], probabylity, maxToll); nextDest = link->getNodeFromIndex(); link = shPath->getInComeLink(nextDest); } };
FPType DescDirectionPathISP::calculateDerivative(Path* path) const{ FPType der = 0.0; FPType flow = 0.0; for (StarLinkIterator it = path->begin(); it != path->end(); ++it) { StarLink* link = *it; flow = link->getFlow(); if (flow < slope_) { flow = slope_; } der += link->getDerivative(); } return der; };
void DAGraph::printShPath(int node){ StarLink *prevMin = (nodes_[node])->minLink; int prevNode = -1; std::cout << "Cost = " << (nodes_[node])->minDist << std::endl; FPType cost = 0.0; while (prevMin != NULL){ prevNode = prevMin->getNodeFromIndex(); cost += prevMin->getTime(); std::cout << "[" << prevMin->getNodeToIndex() << ", " << prevNode << "] " << prevMin->getFlow() << "-"; prevMin = (nodes_[prevNode])->minLink; } std::cout << std::endl; };
void KMLNetOutput::createKML(const std::string& fileWithNodes, const std::string& kmlFileName){ std::cout << "KML will be written to: " << kmlFileName << std::endl; int nbNodes = net_->getNbNodes(); std::vector<FPType> xCoord(nbNodes, 0); std::vector<FPType> yCoord(nbNodes, 0); std::vector<int> nodeID(nbNodes, 0); readCoord(fileWithNodes, xCoord, yCoord, nodeID); FileWriter writeKml(kmlFileName); writeKml.writeLine(createKmlHeader()); for (StarLink* link = net_->beginOnlyLink(); link != NULL; link = net_->getNextOnlyLink()) { if (shouldCreatePlacemark(link)) { int tail = link->getNodeFromIndex(); int head = link->getNodeToIndex(); FPType x1 = xCoord[tail]; FPType y1 = yCoord[tail]; FPType x2 = xCoord[head]; FPType y2 = yCoord[head]; if (x1 == 0 && y1 == 0) std::cout << "Missing node coordinate: " << link->getNodeFrom() << " link: " << link->toString() << std::endl; if (x2 == 0 && y2 == 0) std::cout << "Missing node coordinate: " << link->getNodeTo() << " link: " << link->toString() << std::endl; if (x1 != 0 && y1 != 0 && x2 != 0 && y2 != 0) writeKml.writeLine(createPlacemark(x1, y1, x2, y2, link)); } } writeKml.writeLine(createKmlFooter()); };
FPType DAGraph::checkOFlowsFeasibility(){ int nbNodes = net_->getNbNodes(); FPType total[nbNodes]; for (int i = 0; i < nbNodes; ++i) { total[i] = 0.0; } // load demands for (OriginIterator it = mat_->begin(); it != mat_->end(); ++it){ Origin* origin = *it; if (origin->getIndex() == originIndex_){ for (PairODIterator jt = origin->begin(); jt != origin->end(); ++jt) { PairOD* dest = *jt; FPType demand = dest->getDemand(); total[origin->getIndex()] += demand; total[dest->getIndex()] -= demand; } break; } } //travers network and check int i = -1; StarLink* link = NULL; std::list<StarLink*> inLinks; for (int j = 0; j < nodeSize_; ++j) { i = nodeIndexes_[j]; getInLinks(i, inLinks); for (std::list<StarLink*>::iterator it = inLinks.begin(); it != inLinks.end(); ++it){ link = *it; total[link->getNodeFromIndex()] -= getOriginFlow(link->getIndex()); total[link->getNodeToIndex()] += getOriginFlow(link->getIndex()); } } FPType max = 0.0; for (int i = 0; i < net_->getNbNodes(); ++i) { if (fabs(total[i]) > max) { max = fabs(total[i]); } } return max; };
bool ODSet::improveSet(){ shPath_->calculate(originIndex_, destIndex_, index_); FPType minDist = shPath_->getCost(destIndex_); if (minDist - minDist_ < -zeroFlow_) { // if we add link costs in different order path // costs might not be the same Path *path = new Path(); path->setCurrCost(minDist); StarLink *link = shPath_->getInComeLink(destIndex_); int nextDest = link->getNodeFromIndex(); while (link != NULL) { path->addLinkToPath(link); nextDest = link->getNodeFromIndex(); link = shPath_->getInComeLink(nextDest); } addPath(path); return true; } return false; };
void DAGraph::buildMinMaxTrees(int destIndex){ int index = -1; for (int i = 0; i < nodeSize_; ++i) { index = nodeIndexes_[i]; nodes_[index]->minDist = std::numeric_limits<FPType>::infinity( ); nodes_[index]->maxDist = 0.0; } nodes_[originIndex_]->minDist = 0.0; // set to zero for origin // find shortest and longest paths with positive flow FPType dist = 0.0; FPType time = 0.0; int i = beginAscPass(); assert(originIndex_ == i); //-- TODO: theoretically there might be // an alternative top order that starts with another node -- // not clear what to do in this case StarLink* link = NULL; for (; i != -1; i = getNextAscPass()) { std::list<StarLink*> &linksList = nodes_[i]->incomeLinks; for (std::list<StarLink*>::iterator it = linksList.begin(); it != linksList.end(); ++it) { link = *it; index = link->getNodeFromIndex(); assert(nodes_[index] != NULL); time = link->getTime(); dist = nodes_[index]->minDist + time; // min dist if (dist < nodes_[i]->minDist) { nodes_[i]->minDist = dist; nodes_[i]->minLink = link; } dist = nodes_[index]->maxDist + time; // max dist if (dist >= nodes_[i]->maxDist) { nodes_[i]->maxDist = dist; nodes_[i]->maxLink = link; } } if (i == destIndex) break; } };
void ODSet::projectPathFlowOnLinks(){ FPType flow = 0.0; for (PathIterator pathIt = begin(); pathIt != end(); ++pathIt) { Path* path = *pathIt; flow = path->getFlow() - path->getPrevFlow(); if (fabs(flow) > zeroFlow_) { for (StarLinkIterator it = path->begin(); it != path->end(); ++it) { (*it)->addFlow(flow); } } } for (PathIterator pathIt = begin(); pathIt != end(); ++pathIt) { Path* path = *pathIt; for (StarLinkIterator it = path->begin(); it != path->end(); ++it) { StarLink* link = *it; if (link->getFlow() < zeroFlow_) { link->setFlow(0.0); } link->updateTime(); } } };
FPType DAGraphBWithStep::calcFlowStep(Path* minPath, Path* maxPath) const{ int nbLinks = net_->getNbLinks(); std::vector<FPType> x(nbLinks); std::vector<FPType> y(nbLinks); std::vector<int> indexes(nbLinks); for(StarLinkIterator it = maxPath->begin(); it != maxPath->end(); ++it){ y[(*it)->getIndex()] = 0.0; } for (StarLinkIterator it = minPath->begin(); it != minPath->end(); ++it) { y[(*it)->getIndex()] = 0.0; } int linkIndex = -1; int size = 0; // projecting path direction onto links FPType descDirection = minPath->getCurrCost() - maxPath->getCurrCost(); FPType oFlow = 0.0; FPType maxPathFlow = std::numeric_limits<FPType>::infinity( ); for(StarLinkIterator it = maxPath->begin(); it != maxPath->end(); ++it){ StarLink* link = *it; linkIndex = link->getIndex(); x[linkIndex] = link->getFlow(); y[linkIndex] += descDirection; indexes[size] = linkIndex; ++size; oFlow = getOriginFlow(linkIndex); if (oFlow < maxPathFlow) maxPathFlow = oFlow; } if (maxPathFlow == 0.0) { return 0.0; } for (StarLinkIterator it = minPath->begin(); it != minPath->end(); ++it) { StarLink* link = *it; linkIndex = link->getIndex(); x[linkIndex] = link->getFlow(); y[linkIndex] -= descDirection; indexes[size] = linkIndex; ++size; } (lineSearch_->getDerivative())->setDataPointers(size, x, y, indexes); // calculating upper bound for line search FPType ub = -maxPathFlow / descDirection; assert(ub > 0.0); return (lineSearch_->execute(0.0, ub) * -descDirection); };
void LinkFlows::updateLinkFlows(){ for (StarLink *link = net_->beginOnlyLink(); link != NULL; link = net_->getNextOnlyLink()) { link->setFlow(linkFlows_[link->getIndex()]); link->updateTime(); } };