1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
|
"""
Custom Node class for OdiParPack
"""
import math
class Node:
"""
Attributes
----------
index : int
Index in some arrays
ubigeo : str
6 digit ID
lat : float
Latitud (angulo de los Paralelos) en grados sexagesimales
lon : float
Longitud (angulo de los Meridianos) en grados sexagesimales
is_depot : bool
demand : int
ready_time : float
due_time : float
service_time : float
x : float
Aproximacion local, en Km respecto
y : float
Aproximacion local, en Km respecto ("Lima")
Notes
-----
Web Mercator projection (BAD):
x = floor(256 / (2 * math.pi) * 2**(zoom_level) * (lon + math.pi))
y = floor(265 / (2 * math.pi) * 2**(zoom_level) * (math.pi - math.ln(math.tan( math.pi / 4 + lat / 2 ))))
x = R * lon
y = R * ln(tan(pi/4 + lat/2)
Both `lon` and `lat` in radians.
"Lima": -12.04591952,-77.03049615 (lat, long)
"""
def __init__(self, index: int, ubigeo, lat, lon, is_depot,
demand, ready_time, due_time, service_time):
super()
self.index = index
self.ubigeo = ubigeo
if is_depot:
self.is_depot = True
else:
self.is_depot = False
earth_radius_km = 6371 # Avg. radius
lima_lat = -12.04591952
lima_lon = -77.03049615
self.lat = lat
self.lon = lon
self.x = (lon - lima_lon) * (math.pi / 180) * earth_radius_km
self.y = (lat - lima_lat) * (math.pi / 180) * earth_radius_km
self.x = round(self.x, 3)
self.y = round(self.y, 3)
self.demand = demand
self.ready_time = 0 # ready_time
self.due_time = due_time
self.service_time = service_time
|