0
# Measurements
1
2
Functions for calculating areas, lengths, and distances within the H3 system. These functions provide precise measurements for cells, edges, and distances using spherical geometry calculations, supporting multiple units of measurement.
3
4
## Capabilities
5
6
### Cell Area Measurements
7
8
Calculate the surface area of H3 cells and average areas at different resolutions.
9
10
```python { .api }
11
def cell_area(h: str, unit: str = 'km^2') -> float:
12
"""
13
Calculate the surface area of a specific H3 cell.
14
15
Uses spherical geometry to compute the exact area of the cell
16
on the Earth's surface.
17
18
Args:
19
h: H3 cell identifier
20
unit: Unit for area result:
21
- 'km^2': Square kilometers (default)
22
- 'm^2': Square meters
23
- 'rads^2': Square radians
24
25
Returns:
26
Cell area in specified units
27
28
Raises:
29
H3CellInvalidError: If h is not a valid H3 cell
30
ValueError: If unit is not supported
31
32
Note:
33
Pentagons have slightly different areas than hexagons at the same resolution.
34
Calculation uses spherical triangulation for accuracy.
35
"""
36
37
def average_hexagon_area(res: int, unit: str = 'km^2') -> float:
38
"""
39
Get the average area of hexagon cells at a given resolution.
40
41
This average excludes pentagons and represents typical cell area.
42
43
Args:
44
res: H3 resolution (0-15)
45
unit: Unit for area result:
46
- 'km^2': Square kilometers (default)
47
- 'm^2': Square meters
48
- 'rads^2': Square radians
49
50
Returns:
51
Average hexagon area in specified units
52
53
Raises:
54
H3ResDomainError: If res < 0 or res > 15
55
ValueError: If unit is not supported
56
57
Note:
58
Pentagon areas may differ from this average.
59
Higher resolutions have smaller cell areas (~1/7 per resolution level).
60
"""
61
```
62
63
### Edge Length Measurements
64
65
Calculate the length of H3 edges and average edge lengths at different resolutions.
66
67
```python { .api }
68
def edge_length(e: str, unit: str = 'km') -> float:
69
"""
70
Calculate the length of a specific H3 directed edge.
71
72
Uses spherical geometry to compute the exact length of the edge
73
on the Earth's surface.
74
75
Args:
76
e: H3 directed edge identifier
77
unit: Unit for length result:
78
- 'km': Kilometers (default)
79
- 'm': Meters
80
- 'rads': Radians
81
82
Returns:
83
Edge length in specified units
84
85
Raises:
86
H3DirEdgeInvalidError: If e is not a valid H3 directed edge
87
ValueError: If unit is not supported
88
89
Note:
90
Edge lengths may vary slightly within a resolution due to
91
spherical projection effects and pentagon locations.
92
"""
93
94
def average_hexagon_edge_length(res: int, unit: str = 'km') -> float:
95
"""
96
Get the average edge length of hexagon cells at a given resolution.
97
98
This average excludes pentagon edges and represents typical edge length.
99
100
Args:
101
res: H3 resolution (0-15)
102
unit: Unit for length result:
103
- 'km': Kilometers (default)
104
- 'm': Meters
105
- 'rads': Radians
106
107
Returns:
108
Average hexagon edge length in specified units
109
110
Raises:
111
H3ResDomainError: If res < 0 or res > 15
112
ValueError: If unit is not supported
113
114
Note:
115
Pentagon edge lengths may differ from this average.
116
Higher resolutions have shorter edges (~1/√7 ≈ 0.378 per resolution level).
117
"""
118
```
119
120
### Distance Calculations
121
122
Calculate spherical distances between geographic points.
123
124
```python { .api }
125
def great_circle_distance(
126
latlng1: tuple[float, float],
127
latlng2: tuple[float, float],
128
unit: str = 'km'
129
) -> float:
130
"""
131
Calculate the great circle (spherical) distance between two points.
132
133
Uses the haversine formula to compute the shortest distance between
134
two points on the Earth's surface.
135
136
Args:
137
latlng1: First point as (latitude, longitude) in degrees
138
latlng2: Second point as (latitude, longitude) in degrees
139
unit: Unit for distance result:
140
- 'km': Kilometers (default)
141
- 'm': Meters
142
- 'rads': Radians
143
144
Returns:
145
Spherical distance between points in specified units
146
147
Raises:
148
H3LatLngDomainError: If any coordinate is outside valid range
149
ValueError: If unit is not supported
150
151
Note:
152
This is the same distance calculation used internally by H3
153
for all spherical geometry operations.
154
"""
155
```
156
157
## Usage Examples
158
159
### Cell Area Analysis
160
161
```python
162
import h3
163
164
# Compare cell areas across resolutions
165
print("Cell area comparison across resolutions:")
166
lat, lng = 37.7749, -122.4194 # San Francisco
167
168
for res in range(0, 11, 2): # Every other resolution
169
cell = h3.latlng_to_cell(lat, lng, res)
170
171
# Get actual cell area
172
area_km2 = h3.cell_area(cell, 'km^2')
173
area_m2 = h3.cell_area(cell, 'm^2')
174
175
# Compare to system average
176
avg_area = h3.average_hexagon_area(res, 'km^2')
177
178
cell_type = "pentagon" if h3.is_pentagon(cell) else "hexagon"
179
180
print(f"Resolution {res:2d} ({cell_type:7}): {area_km2:10.3f} km² ({area_m2:12,.0f} m²)")
181
print(f" Average: {avg_area:10.3f} km² (ratio: {area_km2/avg_area:.3f})")
182
print()
183
184
# Show area scaling between resolutions
185
print("Area scaling factors:")
186
for res in range(1, 6):
187
area_coarse = h3.average_hexagon_area(res-1, 'km^2')
188
area_fine = h3.average_hexagon_area(res, 'km^2')
189
scaling = area_coarse / area_fine
190
191
print(f"Resolution {res-1} -> {res}: {scaling:.2f}x smaller")
192
```
193
194
### Pentagon vs Hexagon Area Comparison
195
196
```python
197
import h3
198
199
# Compare pentagon and hexagon areas at the same resolution
200
resolution = 6
201
202
# Get pentagons and a regular hexagon
203
pentagons = h3.get_pentagons(resolution)
204
all_cells = h3.get_res0_cells()
205
hexagon_res0 = [cell for cell in all_cells if not h3.is_pentagon(cell)][0]
206
hexagon = h3.cell_to_children(hexagon_res0, resolution)[0]
207
208
print(f"Area comparison at resolution {resolution}:")
209
210
# Calculate pentagon areas
211
pentagon_areas = []
212
for i, pentagon in enumerate(pentagons[:5]): # Just first 5 pentagons
213
area = h3.cell_area(pentagon, 'km^2')
214
pentagon_areas.append(area)
215
print(f"Pentagon {i+1}: {area:.3f} km²")
216
217
# Calculate hexagon area
218
hexagon_area = h3.cell_area(hexagon, 'km^2')
219
print(f"Hexagon: {hexagon_area:.3f} km²")
220
221
# Statistics
222
avg_pentagon_area = sum(pentagon_areas) / len(pentagon_areas)
223
system_avg = h3.average_hexagon_area(resolution, 'km^2')
224
225
print(f"\nAverage pentagon area: {avg_pentagon_area:.3f} km²")
226
print(f"System average (hexagon): {system_avg:.3f} km²")
227
print(f"Pentagon vs hexagon ratio: {avg_pentagon_area / hexagon_area:.3f}")
228
print(f"Pentagon vs system avg: {avg_pentagon_area / system_avg:.3f}")
229
```
230
231
### Edge Length Analysis
232
233
```python
234
import h3
235
236
# Analyze edge lengths for different cell types
237
resolution = 8
238
239
# Get a regular hexagon
240
center = h3.latlng_to_cell(0, 0, resolution) # Equator
241
pentagon = h3.get_pentagons(resolution)[0]
242
243
print(f"Edge length analysis at resolution {resolution}:")
244
245
# Analyze hexagon edges
246
hex_edges = h3.origin_to_directed_edges(center)
247
hex_edge_lengths = []
248
249
print(f"\nHexagon edges ({len(hex_edges)}):")
250
for i, edge in enumerate(hex_edges):
251
length_km = h3.edge_length(edge, 'km')
252
length_m = h3.edge_length(edge, 'm')
253
hex_edge_lengths.append(length_km)
254
print(f" Edge {i}: {length_km:.3f} km ({length_m:.0f} m)")
255
256
# Analyze pentagon edges
257
pent_edges = h3.origin_to_directed_edges(pentagon)
258
pent_edge_lengths = []
259
260
print(f"\nPentagon edges ({len(pent_edges)}):")
261
for i, edge in enumerate(pent_edges):
262
length_km = h3.edge_length(edge, 'km')
263
length_m = h3.edge_length(edge, 'm')
264
pent_edge_lengths.append(length_km)
265
print(f" Edge {i}: {length_km:.3f} km ({length_m:.0f} m)")
266
267
# Compare to system averages
268
system_avg = h3.average_hexagon_edge_length(resolution, 'km')
269
hex_avg = sum(hex_edge_lengths) / len(hex_edge_lengths)
270
pent_avg = sum(pent_edge_lengths) / len(pent_edge_lengths)
271
272
print(f"\nComparison:")
273
print(f"System average: {system_avg:.3f} km")
274
print(f"Hexagon average: {hex_avg:.3f} km (variation: {abs(hex_avg - system_avg) / system_avg:.1%})")
275
print(f"Pentagon average: {pent_avg:.3f} km (vs system: {pent_avg / system_avg:.3f})")
276
```
277
278
### Distance Calculations
279
280
```python
281
import h3
282
283
# Calculate distances between famous landmarks
284
landmarks = {
285
"San Francisco": (37.7749, -122.4194),
286
"New York": (40.7589, -73.9851),
287
"London": (51.5074, -0.1278),
288
"Tokyo": (35.6762, 139.6503),
289
"Sydney": (-33.8688, 151.2093)
290
}
291
292
print("Great circle distances between major cities:")
293
294
cities = list(landmarks.keys())
295
for i in range(len(cities)):
296
for j in range(i+1, len(cities)):
297
city1, city2 = cities[i], cities[j]
298
coord1, coord2 = landmarks[city1], landmarks[city2]
299
300
# Calculate distance in different units
301
dist_km = h3.great_circle_distance(coord1, coord2, 'km')
302
dist_m = h3.great_circle_distance(coord1, coord2, 'm')
303
dist_rads = h3.great_circle_distance(coord1, coord2, 'rads')
304
305
print(f"{city1:12} - {city2:12}: {dist_km:7.0f} km ({dist_m:10,.0f} m, {dist_rads:.4f} rads)")
306
307
# Verify against H3 cell center distances
308
print(f"\nVerification using H3 cell centers:")
309
resolution = 4 # Coarse resolution for global coverage
310
311
sf_cell = h3.latlng_to_cell(*landmarks["San Francisco"], resolution)
312
ny_cell = h3.latlng_to_cell(*landmarks["New York"], resolution)
313
314
sf_center = h3.cell_to_latlng(sf_cell)
315
ny_center = h3.cell_to_latlng(ny_cell)
316
317
direct_dist = h3.great_circle_distance(landmarks["San Francisco"], landmarks["New York"], 'km')
318
cell_dist = h3.great_circle_distance(sf_center, ny_center, 'km')
319
320
print(f"SF-NY direct: {direct_dist:.0f} km")
321
print(f"SF-NY via H3 cells (res {resolution}): {cell_dist:.0f} km")
322
print(f"Difference: {abs(direct_dist - cell_dist):.0f} km ({abs(direct_dist - cell_dist) / direct_dist:.1%})")
323
```
324
325
### Resolution Scaling Analysis
326
327
```python
328
import h3
329
330
# Analyze how measurements scale across resolutions
331
print("H3 Resolution Scaling Analysis:")
332
print("Resolution | Avg Area (km²) | Avg Edge (km) | Area Ratio | Edge Ratio")
333
print("-" * 70)
334
335
prev_area = None
336
prev_edge = None
337
338
for res in range(0, 16):
339
avg_area = h3.average_hexagon_area(res, 'km^2')
340
avg_edge = h3.average_hexagon_edge_length(res, 'km')
341
342
area_ratio = prev_area / avg_area if prev_area else None
343
edge_ratio = prev_edge / avg_edge if prev_edge else None
344
345
print(f"{res:8d} | {avg_area:12.6f} | {avg_edge:10.6f} | "
346
f"{area_ratio:8.2f} | {edge_ratio:8.2f}" if area_ratio else
347
f"{res:8d} | {avg_area:12.6f} | {avg_edge:10.6f} | - | - ")
348
349
prev_area = avg_area
350
prev_edge = avg_edge
351
352
print(f"\nTheoretical scaling factors:")
353
print(f"Area ratio: ~7.0 (each level has ~1/7 the area)")
354
print(f"Edge ratio: ~√7 ≈ 2.65 (each level has ~1/√7 the edge length)")
355
```
356
357
### Measurement Precision Comparison
358
359
```python
360
import h3
361
import math
362
363
# Compare H3 measurements with theoretical calculations
364
print("Measurement precision analysis:")
365
366
# Test at different latitudes to see projection effects
367
test_points = [
368
("Equator", 0, 0),
369
("Tropical", 23.5, 0), # Tropic of Cancer
370
("Mid-latitude", 45, 0),
371
("High latitude", 60, 0),
372
("Arctic", 80, 0)
373
]
374
375
resolution = 7
376
377
print(f"Resolution {resolution} analysis:")
378
print("Location | Cell Area (km²) | Avg Area | Ratio | Edge Length (km) | Avg Edge | Ratio")
379
print("-" * 95)
380
381
for name, lat, lng in test_points:
382
# Get cell measurements
383
cell = h3.latlng_to_cell(lat, lng, resolution)
384
cell_area = h3.cell_area(cell, 'km^2')
385
386
# Get an edge from this cell
387
edges = h3.origin_to_directed_edges(cell)
388
edge_length = h3.edge_length(edges[0], 'km')
389
390
# Compare to system averages
391
avg_area = h3.average_hexagon_area(resolution, 'km^2')
392
avg_edge = h3.average_hexagon_edge_length(resolution, 'km')
393
394
area_ratio = cell_area / avg_area
395
edge_ratio = edge_length / avg_edge
396
397
print(f"{name:12} | {cell_area:13.6f} | {avg_area:8.6f} | {area_ratio:.3f} | "
398
f"{edge_length:14.6f} | {avg_edge:8.6f} | {edge_ratio:.3f}")
399
```
400
401
### Area Coverage Calculations
402
403
```python
404
import h3
405
406
# Calculate total area coverage for different scenarios
407
print("Area coverage calculations:")
408
409
# Scenario 1: City coverage
410
city_center = h3.latlng_to_cell(37.7749, -122.4194, 8) # San Francisco
411
city_cells = h3.grid_disk(city_center, k=5)
412
413
total_area = sum(h3.cell_area(cell, 'km^2') for cell in city_cells)
414
avg_area = h3.average_hexagon_area(8, 'km^2')
415
approx_area = len(city_cells) * avg_area
416
417
print(f"City coverage (k=5 at resolution 8):")
418
print(f" Cells: {len(city_cells)}")
419
print(f" Exact total area: {total_area:.2f} km²")
420
print(f" Approximate area: {approx_area:.2f} km²")
421
print(f" Difference: {abs(total_area - approx_area):.2f} km² ({abs(total_area - approx_area) / total_area:.1%})")
422
423
# Scenario 2: Country-scale coverage
424
country_polygon = h3.LatLngPoly([
425
(49.0, -125.0), (49.0, -66.0), (25.0, -66.0), (25.0, -125.0) # Rough USA bounds
426
])
427
428
country_cells = h3.h3shape_to_cells(country_polygon, 4) # Coarse resolution
429
country_area = sum(h3.cell_area(cell, 'km^2') for cell in country_cells)
430
usa_actual_area = 9834000 # km² (approximate)
431
432
print(f"\nCountry coverage (USA approximation at resolution 4):")
433
print(f" Cells: {len(country_cells)}")
434
print(f" H3 calculated area: {country_area:,.0f} km²")
435
print(f" Actual USA area: {usa_actual_area:,.0f} km²")
436
print(f" Coverage ratio: {country_area / usa_actual_area:.3f}")
437
438
# Show the impact of resolution on coverage accuracy
439
print(f"\nResolution impact on area calculation:")
440
for res in [3, 4, 5, 6]:
441
cells = h3.h3shape_to_cells(country_polygon, res)
442
area = sum(h3.cell_area(cell, 'km^2') for cell in cells)
443
ratio = area / usa_actual_area
444
print(f" Resolution {res}: {len(cells):6,} cells, {area:9,.0f} km² (ratio: {ratio:.3f})")
445
```