| 197 | } |
| 198 | |
| 199 | void TransitGraph::Fill(::transit::experimental::TransitData const & transitData, Endings const & stopEndings, |
| 200 | Endings const & gateEndings) |
| 201 | { |
| 202 | CHECK_EQUAL(m_transitVersion, ::transit::TransitVersion::AllPublicTransport, ()); |
| 203 | |
| 204 | for (auto const & line : transitData.GetLines()) |
| 205 | m_transferPenaltiesPT[line.GetId()] = line.GetSchedule(); |
| 206 | |
| 207 | map<transit::StopId, LatLonWithAltitude> stopCoords; |
| 208 | |
| 209 | for (auto const & stop : transitData.GetStops()) |
| 210 | { |
| 211 | stopCoords[stop.GetId()] = |
| 212 | LatLonWithAltitude(mercator::ToLatLon(stop.GetPoint()), geometry::kDefaultAltitudeMeters); |
| 213 | } |
| 214 | |
| 215 | StopToSegmentsMap stopToBack; |
| 216 | StopToSegmentsMap stopToFront; |
| 217 | StopToSegmentsMap outgoing; |
| 218 | StopToSegmentsMap ingoing; |
| 219 | |
| 220 | // It's important to add transit edges first to ensure fake segment id for particular edge is edge |
| 221 | // order in mwm. We use edge fake segments in cross-mwm section and they should be stable. |
| 222 | auto const & edges = transitData.GetEdges(); |
| 223 | CHECK_EQUAL(m_fake.GetSize(), 0, ()); |
| 224 | for (size_t i = 0; i < edges.size(); ++i) |
| 225 | { |
| 226 | auto const & edge = edges[i]; |
| 227 | CHECK_NOT_EQUAL(edge.GetWeight(), transit::kInvalidWeight, ("Edge should have valid weight.")); |
| 228 | auto const edgeSegment = AddEdge(edge, stopCoords, stopToBack, stopToFront); |
| 229 | // Checks fake feature ids have consecutive numeration starting from |
| 230 | // FakeFeatureIds::kTransitGraphFeaturesStart. |
| 231 | CHECK_EQUAL(edgeSegment.GetFeatureId(), i + FakeFeatureIds::kTransitGraphFeaturesStart, ()); |
| 232 | outgoing[edge.GetStop1Id()].insert(edgeSegment); |
| 233 | ingoing[edge.GetStop2Id()].insert(edgeSegment); |
| 234 | } |
| 235 | CHECK_EQUAL(m_fake.GetSize(), edges.size(), ()); |
| 236 | |
| 237 | for (auto const & gate : transitData.GetGates()) |
| 238 | { |
| 239 | CHECK(!gate.GetStopsWithWeight().empty(), ("Gate should have valid weight.", gate)); |
| 240 | |
| 241 | // Gate ending may have empty projections vector. It means gate is not connected to roads. |
| 242 | auto const it = gateEndings.find(gate.GetOsmId()); |
| 243 | if (it != gateEndings.end()) |
| 244 | { |
| 245 | if (gate.IsEntrance()) |
| 246 | AddGate(gate, it->second, stopCoords, true /* isEnter */, stopToBack, stopToFront); |
| 247 | if (gate.IsExit()) |
| 248 | AddGate(gate, it->second, stopCoords, false /* isEnter */, stopToBack, stopToFront); |
| 249 | } |
| 250 | } |
| 251 | |
| 252 | for (auto const & stop : transitData.GetStops()) |
| 253 | { |
| 254 | // Stop ending may have empty projections vector. It means stop is not connected to roads. |
| 255 | auto const it = stopEndings.find(stop.GetId()); |
| 256 | if (it != stopEndings.end()) |
no test coverage detected