buses.py

changeset 109
88a5110b66ba
parent 94
e27c18f080d1
child 114
b736478416d4
equal deleted inserted replaced
108:4b09d8a597f8 109:88a5110b66ba
96 break 96 break
97 # ja siirry seuraavaan päivään. 97 # ja siirry seuraavaan päivään.
98 date += timedelta(1) 98 date += timedelta(1)
99 # Typistä lopputulos haluttuun tulosmäärään. 99 # Typistä lopputulos haluttuun tulosmäärään.
100 return result[:max_amount] 100 return result[:max_amount]
101 def schedule_for_day(self, date, *, arrivals = False): 101 def schedule_for_day(self, date, *, arrivals = False, allow_gone = False):
102 ''' 102 '''
103 Hakee pysäkin aikataulut tiettynä päivänä. 103 Hakee pysäkin aikataulut tiettynä päivänä.
104 ''' 104 '''
105 # Jos päädyttiin aikataulukalenterin ulkopuolelle, niin tuotetaan virhe. Jos vain 105 # Jos päädyttiin aikataulukalenterin ulkopuolelle, niin tuotetaan virhe. Jos vain
106 # palautettaisiin tyhjä result, niin algoritmi jatkaisi etsintää loputtomiin. 106 # palautettaisiin tyhjä result, niin algoritmi jatkaisi etsintää loputtomiin.
115 # päätepysäkille, 115 # päätepysäkille,
116 stop = trip.contains_stop(self) 116 stop = trip.contains_stop(self)
117 if stop and (arrivals or not stop.is_arrival) and stop is not trip.schedule[-1]: 117 if stop and (arrivals or not stop.is_arrival) and stop is not trip.schedule[-1]:
118 # ja jos tämä halt on tulevaisuudessa, 118 # ja jos tämä halt on tulevaisuudessa,
119 stop_time = datetime.combine(date, time()) + stop.departure_time 119 stop_time = datetime.combine(date, time()) + stop.departure_time
120 if stop_time + timedelta(minutes = 1) >= now(): 120 if allow_gone or (stop_time + timedelta(minutes = 1) >= now()):
121 # lisää halt listaan. 121 # lisää halt listaan.
122 result.append({ 122 result.append({
123 'date': date, 123 'date': date,
124 'offset': stop.departure_time, 124 'offset': stop.departure_time,
125 'time': stop_time, 125 'time': stop_time,
179 route = self.trip.concise_schedule(self), 179 route = self.trip.concise_schedule(self),
180 trip_length = self.trip.length - self.traveled_distance, 180 trip_length = self.trip.length - self.traveled_distance,
181 long = long, 181 long = long,
182 ) 182 )
183 183
184 class BusStopCluster:
185 def __init__(self):
186 self.stops = set()
187 self.cached_center = None
188 self.name = None
189 @property
190 def url_name(self):
191 return self.name.lower().replace('(', '').replace(')', '').replace(' ', '-')
192 def add_stop(self, stop):
193 assert not stop.cluster
194 stop.cluster = self
195 self.stops.add(stop)
196 self.cached_center = None
197 @property
198 def center(self):
199 if not self.cached_center:
200 if self.stops:
201 from statistics import median
202 pointtype = type(next(iter(self.stops)).location)
203 self.cached_center = pointtype(
204 median(stop.location.x for stop in self.stops),
205 median(stop.location.y for stop in self.stops),
206 )
207 else:
208 raise ValueError('an empty cluster has no center point')
209 return self.cached_center
210 def merge(self, other):
211 for bus_stop in other.stops:
212 bus_stop.cluster = self
213 self.stops |= other.stops
214 other.stops = set()
215 other.cached_center = None
216 def schedule(self, *, max_amount = 50):
217 result = []
218 for stop in self.stops:
219 result += stop.schedule(max_amount = max_amount)
220 result.sort(key = lambda schedule_entry: schedule_entry['time'])
221 return result[:max_amount]
222
223 class CustomBusStopCluster(BusStopCluster):
224 def __init__(self, *, name, stops):
225 super().__init__()
226 self.name = name
227 self.stops = stops
228 def add_stop(self, stop):
229 return NotImplemented
230 @property
231 def url_name(self):
232 from urllib.request import quote
233 return 'custom?stops=' + ';'.join(stop.code for stop in self.stops) + '&name=' + quote(self.name)
234
184 routes = {} 235 routes = {}
185 routes_per_id = {} 236 routes_per_id = {}
186 all_trips = {} 237 all_trips = {}
187 services = {} 238 services = {}
188 bus_stops = {} 239 bus_stops = {}
317 pass 368 pass
318 for bus_stop in bus_stops.values(): 369 for bus_stop in bus_stops.values():
319 if not hasattr(bus_stop, 'region'): 370 if not hasattr(bus_stop, 'region'):
320 bus_stop.region = None 371 bus_stop.region = None
321 print('%d stops' % len(bus_stops), file = stderr) 372 print('%d stops' % len(bus_stops), file = stderr)
322
323 class BusStopCluster:
324 def __init__(self):
325 self.stops = set()
326 self.cached_center = None
327 self.name = None
328 @property
329 def url_name(self):
330 return self.name.lower().replace('(', '').replace(')', '').replace(' ', '-')
331 def add_stop(self, stop):
332 assert not stop.cluster
333 stop.cluster = self
334 self.stops.add(stop)
335 self.cached_center = None
336 @property
337 def center(self):
338 if not self.cached_center:
339 if self.stops:
340 from statistics import median
341 pointtype = type(next(iter(self.stops)).location)
342 self.cached_center = pointtype(
343 median(stop.location.x for stop in self.stops),
344 median(stop.location.y for stop in self.stops),
345 )
346 else:
347 raise ValueError('an empty cluster has no center point')
348 return self.cached_center
349 def merge(self, other):
350 for bus_stop in other.stops:
351 bus_stop.cluster = self
352 self.stops |= other.stops
353 other.stops = set()
354 other.cached_center = None
355 def schedule(self, *, max_amount = 50):
356 result = []
357 for stop in self.stops:
358 result += stop.schedule(max_amount = max_amount)
359 result.sort(key = lambda schedule_entry: schedule_entry['time'])
360 return result[:max_amount]
361 373
362 from collections import defaultdict 374 from collections import defaultdict
363 bus_stops_by_name = defaultdict(set) 375 bus_stops_by_name = defaultdict(set)
364 for bus_stop in bus_stops.values(): 376 for bus_stop in bus_stops.values():
365 bus_stops_by_name[bus_stop.name].add(bus_stop) 377 bus_stops_by_name[bus_stop.name].add(bus_stop)

mercurial