RDG-Networks 0.1.8__py3-none-any.whl → 0.2.0__py3-none-any.whl

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: RDG-Networks
3
- Version: 0.1.8
3
+ Version: 0.2.0
4
4
  Summary: Most of the code from the RDG Networks project
5
5
  Home-page: https://github.com/NiekMooij/RDG_networks
6
6
  Author: Niek Mooij
@@ -36,6 +36,7 @@ This Python package provides code regarding the RDG networks project.
36
36
  - **generate_line_segments:** Function that determines the linesegments of a RDG network.
37
37
  - **generate_line_network:** Function that makes the underlying network of the linesegments.
38
38
  - **get_intersection_segments:** Function that determines the intersection segments of a RDG network.
39
+ - **generate_line_segments_dynamic:** Function that determines the segments of a dynamic RDG network (with increasing linelengths in time).
39
40
  - **draw_segments:** Function that draws the segments.
40
41
 
41
42
 
@@ -1,13 +1,14 @@
1
1
  RDG_networks/Classes.py,sha256=_9X3JPHFAYYlaC8IZ_H9__sfz99G5l9UfPl65lL60_4,7977
2
- RDG_networks/__init__.py,sha256=lbEZ5NwKERxQ4oLXTxWoe8q8f6c_iSx4ZQXDwgx_OP4,759
2
+ RDG_networks/__init__.py,sha256=aCfGs87cJn0Tp5GqTpFXPOEfJPpR4Tnnz819Kk_0t84,661
3
3
  RDG_networks/draw_segments.py,sha256=U53N5GXmQHWKdM1Q1faP_EGKjc6enOu2mcsunzSFpP0,984
4
4
  RDG_networks/generate_line_network.py,sha256=lJ4rhObim3WcEQoebomewRQKWNJC5phFyFYRW7qjXIg,1127
5
5
  RDG_networks/generate_line_segments.py,sha256=QV8_k7q6TD5c7Hcb2Ms_apEdWYw4XdLr7rdJgh49v4Q,9004
6
+ RDG_networks/generate_line_segments_dynamic.py,sha256=6WaGHnJ-sDmDdyfqh1I-_x5UJCi_1cU2frlPTJYMPoo,7180
6
7
  RDG_networks/get_intersection_segments.py,sha256=mXB5qCy1oOps4Vu1mX6flW6v_4Xxc71YK41yOWjJX8o,2797
7
8
  RDG_networks/sample_in_polygon.py,sha256=qpPpW-Da1vK8ZkVWMJ0zBsE8IgyMB619gCdybSkzKSQ,1605
8
- RDG_Networks-0.1.8.dist-info/LICENSE.txt,sha256=Zlv8517YKFuHaaqksoTKeIiQBl9DGxhUdb_0kJg0NOE,1066
9
- RDG_Networks-0.1.8.dist-info/METADATA,sha256=7oAfTrYytPyZIzFIQu5PhIvvJ_hn0G_BNqw8uAXC1uU,1756
10
- RDG_Networks-0.1.8.dist-info/WHEEL,sha256=Xo9-1PvkuimrydujYJAjF7pCkriuXBpUPEjma1nZyJ0,92
11
- RDG_Networks-0.1.8.dist-info/entry_points.txt,sha256=4LC5qJH7VKpjuuhDR3HpJulO4qy9K5UlAUOGBg6ctxA,268
12
- RDG_Networks-0.1.8.dist-info/top_level.txt,sha256=4gUUYafD5Al9V8ZSiViVGYHpRMMCsCBcGgCNodk9Syg,13
13
- RDG_Networks-0.1.8.dist-info/RECORD,,
9
+ RDG_Networks-0.2.0.dist-info/LICENSE.txt,sha256=Zlv8517YKFuHaaqksoTKeIiQBl9DGxhUdb_0kJg0NOE,1066
10
+ RDG_Networks-0.2.0.dist-info/METADATA,sha256=KJ84ROI4GhdhdpYIQdPFIWMKNeHOMh1C_lkVxcHccb0,1896
11
+ RDG_Networks-0.2.0.dist-info/WHEEL,sha256=Xo9-1PvkuimrydujYJAjF7pCkriuXBpUPEjma1nZyJ0,92
12
+ RDG_Networks-0.2.0.dist-info/entry_points.txt,sha256=Htsh9jRabMCGHwXayUwZoSy-9IFGFrMB1X9hgyyr3_8,350
13
+ RDG_Networks-0.2.0.dist-info/top_level.txt,sha256=4gUUYafD5Al9V8ZSiViVGYHpRMMCsCBcGgCNodk9Syg,13
14
+ RDG_Networks-0.2.0.dist-info/RECORD,,
@@ -2,4 +2,5 @@
2
2
  draw_segments = RDG_networks.draw_segments:main
3
3
  generate_line_network = RDG_networks.generate_line_network:main
4
4
  generate_line_segments = RDG_networks.generate_line_segments:main
5
+ generate_line_segments_dynamic = RDG_networks.generate_line_segments_dynamic:main
5
6
  get_intersection_segments = RDG_networks.get_intersection_segments:main
RDG_networks/__init__.py CHANGED
@@ -1,16 +1,16 @@
1
1
  # __init__.py
2
2
 
3
- # Import important classes, functions, or variables that you want to make available when the package is imported.
4
3
  from .Classes import Line, LineSegment, Polygon
5
4
  from .generate_line_segments import generate_line_segments
6
5
  from .generate_line_network import generate_line_network
7
6
  from .get_intersection_segments import get_intersection_segments
7
+ from .generate_line_segments_dynamic import generate_line_segments_dynamic
8
8
  from .draw_segments import draw_segments
9
9
 
10
- # Define the __all__ variable to specify what should be imported when using "from my_package import *".
11
10
  __all__ = ['generate_line_segments',
12
11
  'generate_line_network',
13
12
  'get_intersection_segments',
13
+ 'generate_line_segments_dynamic',
14
14
  'draw_segments',
15
15
  'sample_in_polygon',
16
16
  'Line',
@@ -0,0 +1,197 @@
1
+ import numpy as np
2
+ import random
3
+ from shapely.geometry import LineString
4
+ from typing import List, Dict, Any, Tuple
5
+
6
+ from .Classes import LineSegment
7
+
8
+ def grow_lines(lines: List[Dict[str, Any]], epsilon: float) -> List[Dict[str, Any]]:
9
+ """
10
+ Grows lines based on their current status.
11
+
12
+ Args:
13
+ lines (List[Dict[str, Any]]): A list of dictionaries representing lines, each containing keys
14
+ 'growth_status', 'end', and 'angle'.
15
+ epsilon (float): The amount by which to grow the lines.
16
+
17
+ Returns:
18
+ List[Dict[str, Any]]: A list of dictionaries representing the updated lines after growth.
19
+ """
20
+ for index, line in enumerate(lines):
21
+ if line['growth_status']:
22
+ # Update the end point of the line based on epsilon and angle
23
+ lines[index]['end'] = (
24
+ line['end'][0] + epsilon * np.cos(line['angle']),
25
+ line['end'][1] + epsilon * np.sin(line['angle'])
26
+ )
27
+
28
+ return lines
29
+
30
+ def add_new_line(lines: List[Dict[str, Any]], line_id: str, t_total: float, angles='uniform') -> List[Dict[str, Any]]:
31
+ """
32
+ Adds a new line and its mirror line to the list of lines.
33
+
34
+ Args:
35
+ lines (List[Dict[str, Any]]): A list of dictionaries representing existing lines.
36
+ line_id (str): The identifier for the new line.
37
+ t_total (float): The total time elapsed.
38
+ angles (str) or List: The allowed anfles in the system.
39
+
40
+ Returns:
41
+ List[Dict[str, Any]]: The updated list of lines after adding the new line and its mirror line.
42
+ """
43
+ np_x = random.uniform(0, 1)
44
+ np_y = random.uniform(0, 1)
45
+
46
+ if angles == 'uniform':
47
+ angle = random.uniform(-np.pi, np.pi)
48
+
49
+ else:
50
+ angle = random.choice(angles)
51
+
52
+ # Create the first line
53
+ line_new_1 = {
54
+ 'id': f'{line_id}_1',
55
+ 'introduction_time': t_total,
56
+ 'neighbors_initial': [],
57
+ 'start': (np_x, np_y),
58
+ 'end': (np_x, np_y),
59
+ 'angle': angle,
60
+ 'growth_status': True
61
+ }
62
+
63
+ # Create the mirror line
64
+ line_new_2 = line_new_1.copy()
65
+ line_new_2['id'] = f'{line_id}_2'
66
+ line_new_2['angle'] = angle + np.pi
67
+
68
+ # Add both lines to the list
69
+ lines.extend([line_new_1, line_new_2])
70
+
71
+ return lines
72
+
73
+ def update_for_border_intersections(lines: List[Dict[str, Any]]) -> List[Dict[str, Any]]:
74
+ """
75
+ Update lines that intersect with the border.
76
+
77
+ Args:
78
+ lines (List[Dict[str, Any]]): A list of dictionaries representing lines.
79
+
80
+ Returns:
81
+ List[Dict[str, Any]]: The updated list of lines after handling border intersections.
82
+ """
83
+ for index, line in enumerate(lines):
84
+ if lines[index]['growth_status'] == True and (line['end'][0] < 0 or line['end'][0] > 1 or line['end'][1] < 0 or line['end'][1] > 1):
85
+ # If line has intersected with the border, update its properties
86
+ lines[index]['neighbors_initial'] = lines[index]['neighbors_initial'] + ['border']
87
+ lines[index]['growth_status'] = False
88
+
89
+ return lines
90
+
91
+ def check_and_update_when_intersect(lines: List[Dict[str, Any]], epsilon: float) -> List[Dict[str, Any]]:
92
+ """
93
+ Check for intersections between lines and update their properties accordingly.
94
+
95
+ Args:
96
+ lines (List[Dict[str, Any]]): A list of dictionaries representing lines.
97
+ epsilon (float): The growth rate of the lines.
98
+
99
+ Returns:
100
+ List[Dict[str, Any]]: The updated list of lines after handling intersections.
101
+ """
102
+ for index1, j1 in enumerate(lines):
103
+ for index2, j2 in enumerate(lines):
104
+ if j1['id'][:-2] == j2['id'][:-2] or index2 < index1:
105
+ continue
106
+
107
+ line1 = LineString([j1['start'], j1['end']])
108
+ line2 = LineString([j2['start'], j2['end']])
109
+
110
+ intersection_pt = line1.intersection(line2)
111
+
112
+ if not intersection_pt.is_empty:
113
+ d1 = np.linalg.norm(np.array(j1['start']) - np.array([intersection_pt.x, intersection_pt.y]))
114
+ d2 = np.linalg.norm(np.array(j2['start']) - np.array([intersection_pt.x, intersection_pt.y]))
115
+
116
+ arrival_1 = j1['introduction_time'] + d1 / epsilon
117
+ arrival_2 = j2['introduction_time'] + d2 / epsilon
118
+
119
+ if arrival_1 > arrival_2:
120
+ lines[index1]['end'] = (intersection_pt.x, intersection_pt.y)
121
+ lines[index1]['neighbors_initial'] = lines[index1]['neighbors_initial'] + [j2['id'][:-2]]
122
+ lines[index1]['growth_status'] = False
123
+
124
+ else:
125
+ lines[index2]['end'] = (intersection_pt.x, intersection_pt.y)
126
+ lines[index2]['neighbors_initial'] = lines[index2]['neighbors_initial'] + [j1['id'][:-2]]
127
+ lines[index2]['growth_status'] = False
128
+
129
+ return lines
130
+
131
+ def transform_to_standard_lines(lines: List[Dict[str, Any]]) -> List[LineSegment]:
132
+ """
133
+ Transform a list of lines into a list of standard line segments.
134
+
135
+ Args:
136
+ lines (List[Dict[str, Any]]): A list of dictionaries representing lines.
137
+
138
+ Returns:
139
+ List[LineSegment]: A list of LineSegment objects representing standard line segments.
140
+ """
141
+ segments = []
142
+ for index in range(0, len(lines), 2):
143
+ s1 = lines[index]
144
+ s2 = lines[index + 1]
145
+
146
+ id = s1['id'][:-2]
147
+ start = s1['end']
148
+ end = s2['end']
149
+
150
+ neighbors = [s1['neighbors_initial'], s2['neighbors_initial']]
151
+
152
+ line_segment = LineSegment(start=start, end=end, id=id, neighbors_initial=neighbors)
153
+ segments.append(line_segment)
154
+
155
+ return segments
156
+
157
+ def generate_line_segments_dynamic(size: int, dt: float, epsilon: float, time: float) -> List[LineSegment]:
158
+ """
159
+ Generate line segments dynamically based on growth and intersection conditions.
160
+
161
+ Args:
162
+ size (int): The desired number of line segments.
163
+ dt (float): Time increment.
164
+ epsilon (float): Growth rate of the lines.
165
+ time (float): Interval at which new lines are added.
166
+
167
+ Returns:
168
+ List[LineSegment]: A list of LineSegment objects representing standard line segments.
169
+ """
170
+ lines = []
171
+ line_id, t, t_total = 1, 0, 0
172
+
173
+ # Stop loop whenever we have enough lines and all lines have stopped growing
174
+ while len(lines) / 2 < size or np.any([item['growth_status'] for item in lines]):
175
+
176
+ t += dt
177
+ t_total += dt
178
+
179
+ if t > time and len(lines) / 2 < size:
180
+
181
+ if time == 0:
182
+ number_of_lines_to_add = size
183
+ else:
184
+ number_of_lines_to_add = int(t - (t % time))
185
+ for _ in range(number_of_lines_to_add):
186
+ lines = add_new_line(lines, line_id, t_total)
187
+ line_id += 1
188
+
189
+ t = 0
190
+
191
+ lines = grow_lines(lines, epsilon)
192
+ lines = update_for_border_intersections(lines)
193
+ lines = check_and_update_when_intersect(lines, epsilon)
194
+
195
+ lines = transform_to_standard_lines(lines)
196
+
197
+ return lines