streetlos 0.1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- streetlos-0.1.0/CHANGELOG.md +19 -0
- streetlos-0.1.0/CITATION.cff +20 -0
- streetlos-0.1.0/LICENSE +21 -0
- streetlos-0.1.0/MANIFEST.in +9 -0
- streetlos-0.1.0/PKG-INFO +298 -0
- streetlos-0.1.0/README.md +263 -0
- streetlos-0.1.0/examples/quickstart.py +54 -0
- streetlos-0.1.0/examples/segments.csv +5 -0
- streetlos-0.1.0/pyproject.toml +107 -0
- streetlos-0.1.0/setup.cfg +4 -0
- streetlos-0.1.0/src/streetlos/__init__.py +68 -0
- streetlos-0.1.0/src/streetlos/__main__.py +7 -0
- streetlos-0.1.0/src/streetlos/_version.py +1 -0
- streetlos-0.1.0/src/streetlos/batch.py +328 -0
- streetlos-0.1.0/src/streetlos/cli.py +93 -0
- streetlos-0.1.0/src/streetlos/comfort.py +140 -0
- streetlos-0.1.0/src/streetlos/py.typed +0 -0
- streetlos-0.1.0/src/streetlos/segment.py +249 -0
- streetlos-0.1.0/src/streetlos/tables.py +194 -0
- streetlos-0.1.0/src/streetlos/timespace.py +149 -0
- streetlos-0.1.0/src/streetlos/units.py +44 -0
- streetlos-0.1.0/src/streetlos/walkway.py +193 -0
- streetlos-0.1.0/src/streetlos.egg-info/PKG-INFO +298 -0
- streetlos-0.1.0/src/streetlos.egg-info/SOURCES.txt +32 -0
- streetlos-0.1.0/src/streetlos.egg-info/dependency_links.txt +1 -0
- streetlos-0.1.0/src/streetlos.egg-info/entry_points.txt +2 -0
- streetlos-0.1.0/src/streetlos.egg-info/requires.txt +6 -0
- streetlos-0.1.0/src/streetlos.egg-info/top_level.txt +1 -0
- streetlos-0.1.0/tests/test_batch_cli.py +179 -0
- streetlos-0.1.0/tests/test_comfort.py +61 -0
- streetlos-0.1.0/tests/test_segment.py +215 -0
- streetlos-0.1.0/tests/test_tables.py +116 -0
- streetlos-0.1.0/tests/test_timespace.py +78 -0
- streetlos-0.1.0/tests/test_walkway.py +109 -0
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
## [Unreleased]
|
|
6
|
+
|
|
7
|
+
## [0.1.0] - 2026-11-09
|
|
8
|
+
### Added
|
|
9
|
+
- Walkway LOS by space per pedestrian and unit flow rate, with average-flow and
|
|
10
|
+
platoon-adjusted criteria (FHWA-RD-98-107; HCM 2000 walkway tables).
|
|
11
|
+
- Effective sidewalk width with building and curb shy distances and street furniture.
|
|
12
|
+
- Corner and crosswalk circulation area with the time-space method.
|
|
13
|
+
- Pedestrian and bicycle segment (link) LOS score models of NCHRP Report 616 in the
|
|
14
|
+
HCM 2010 form, returning every factor.
|
|
15
|
+
- Pedestrian comfort and bicycle facility indicators with configurable thresholds
|
|
16
|
+
(PROWAG clear-width minimum).
|
|
17
|
+
- Overridable, cited `LosTable` threshold tables.
|
|
18
|
+
- `streetlos` command line tool: CSV of segments in, LOS table out, US or SI units,
|
|
19
|
+
JSON table overrides.
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
cff-version: 1.2.0
|
|
2
|
+
message: "If you use this software, please cite it as below."
|
|
3
|
+
authors:
|
|
4
|
+
- family-names: "Eminoğlu"
|
|
5
|
+
given-names: "Yusuf"
|
|
6
|
+
email: "geospacephilo@gmail.com"
|
|
7
|
+
orcid: "https://orcid.org/0009-0005-6000-2934"
|
|
8
|
+
title: "streetlos"
|
|
9
|
+
version: "0.1.0"
|
|
10
|
+
date-released: "2026-11-09"
|
|
11
|
+
license: "MIT"
|
|
12
|
+
repository-code: "https://gitlab.com/geophilo1/streetlos_sdk"
|
|
13
|
+
url: "https://pypi.org/project/streetlos/"
|
|
14
|
+
abstract: "Multimodal street level-of-service screening: walkway LOS by flow and space (average and platoon-adjusted), corner and crosswalk circulation area, NCHRP Report 616 / HCM 2010 pedestrian and bicycle segment LOS scores, and comfort indicators, with a CSV command line tool."
|
|
15
|
+
keywords:
|
|
16
|
+
- level of service
|
|
17
|
+
- pedestrian
|
|
18
|
+
- bicycle
|
|
19
|
+
- complete streets
|
|
20
|
+
- transportation planning
|
streetlos-0.1.0/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Yusuf Eminoğlu
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
streetlos-0.1.0/PKG-INFO
ADDED
|
@@ -0,0 +1,298 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: streetlos
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Multimodal street level-of-service screening: walkway LOS by flow and space (average and platoon-adjusted), corner and crosswalk circulation area, NCHRP 616 / HCM 2010 pedestrian and bicycle segment LOS scores, and comfort indicators, with a CSV command line tool.
|
|
5
|
+
Author-email: Yusuf Eminoğlu <geospacephilo@gmail.com>
|
|
6
|
+
License-Expression: MIT
|
|
7
|
+
Project-URL: Homepage, https://gitlab.com/geophilo1/streetlos_sdk
|
|
8
|
+
Project-URL: Repository, https://gitlab.com/geophilo1/streetlos_sdk
|
|
9
|
+
Project-URL: Issues, https://gitlab.com/geophilo1/streetlos_sdk/-/work_items
|
|
10
|
+
Project-URL: Changelog, https://gitlab.com/geophilo1/streetlos_sdk/-/blob/main/CHANGELOG.md
|
|
11
|
+
Keywords: level-of-service,multimodal-los,pedestrian,bicycle,walkability,sidewalk,complete-streets,highway-capacity-manual,nchrp-616,transportation-planning,urban-planning,gis
|
|
12
|
+
Classifier: Development Status :: 4 - Beta
|
|
13
|
+
Classifier: Programming Language :: Python :: 3
|
|
14
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
19
|
+
Classifier: Operating System :: OS Independent
|
|
20
|
+
Classifier: Environment :: Console
|
|
21
|
+
Classifier: Topic :: Scientific/Engineering :: GIS
|
|
22
|
+
Classifier: Topic :: Scientific/Engineering
|
|
23
|
+
Classifier: Intended Audience :: Science/Research
|
|
24
|
+
Classifier: Intended Audience :: Developers
|
|
25
|
+
Classifier: Typing :: Typed
|
|
26
|
+
Requires-Python: >=3.9
|
|
27
|
+
Description-Content-Type: text/markdown
|
|
28
|
+
License-File: LICENSE
|
|
29
|
+
Provides-Extra: dev
|
|
30
|
+
Requires-Dist: pytest>=7.0.0; extra == "dev"
|
|
31
|
+
Requires-Dist: pytest-cov>=4.0.0; extra == "dev"
|
|
32
|
+
Requires-Dist: ruff>=0.1.0; extra == "dev"
|
|
33
|
+
Requires-Dist: mypy>=1.0.0; extra == "dev"
|
|
34
|
+
Dynamic: license-file
|
|
35
|
+
|
|
36
|
+
# streetlos
|
|
37
|
+
|
|
38
|
+
[](https://pypi.org/project/streetlos/)
|
|
39
|
+
[](https://pypi.org/project/streetlos/)
|
|
40
|
+
[](https://gitlab.com/geophilo1/streetlos_sdk/-/pipelines)
|
|
41
|
+
[](https://gitlab.com/geophilo1/streetlos_sdk/-/blob/main/LICENSE)
|
|
42
|
+
|
|
43
|
+
**Multimodal street level-of-service screening for walking and cycling.**
|
|
44
|
+
|
|
45
|
+
`streetlos` scores street segments for pedestrians and cyclists from a plain CSV
|
|
46
|
+
of street attributes. It is written for planners and researchers who need a
|
|
47
|
+
transparent, reproducible screening (which streets look poor, and why) rather
|
|
48
|
+
than a black box. Every threshold table is cited and can be overridden.
|
|
49
|
+
|
|
50
|
+
- **Walkway LOS** by space per pedestrian and unit flow rate, with the
|
|
51
|
+
average-flow and the **platoon-adjusted** criteria.
|
|
52
|
+
- **Effective sidewalk width** after shy distances and street furniture.
|
|
53
|
+
- **Corner and crosswalk circulation area** with the time-space method.
|
|
54
|
+
- **Pedestrian and bicycle segment LOS scores** from NCHRP Report 616
|
|
55
|
+
(Dowling et al. 2008), in the form adopted by HCM 2010.
|
|
56
|
+
- **Comfort indicators**: clear width against the PROWAG minimum, buffer,
|
|
57
|
+
traffic speed and volume per lane, bike lane width and door-zone exposure.
|
|
58
|
+
- **CLI**: CSV of segments in, LOS table out. US (ft, mph) or SI (m, km/h) units.
|
|
59
|
+
|
|
60
|
+
No runtime dependencies: the standard library is enough.
|
|
61
|
+
|
|
62
|
+
```bash
|
|
63
|
+
pip install streetlos
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
Requires Python 3.9 or newer.
|
|
67
|
+
|
|
68
|
+
> **About the HCM.** The *Highway Capacity Manual* is a copyrighted publication
|
|
69
|
+
> of the Transportation Research Board. `streetlos` does not reproduce its text.
|
|
70
|
+
> It implements published equations and numeric thresholds, cites the openly
|
|
71
|
+
> accessible documents they were checked against, and lets you replace every
|
|
72
|
+
> table (for example with the values of the HCM edition your agency uses).
|
|
73
|
+
|
|
74
|
+
---
|
|
75
|
+
|
|
76
|
+
## Quickstart
|
|
77
|
+
|
|
78
|
+
```python
|
|
79
|
+
import streetlos as sl
|
|
80
|
+
|
|
81
|
+
# Walkway: 8.5 ft effective width, 600 pedestrians in the peak 15 minutes
|
|
82
|
+
w = sl.walkway_los(8.5, 600)
|
|
83
|
+
print(w.unit_flow_p_min_ft, w.space_ft2_p, w.los) # 4.71 56.1 'B'
|
|
84
|
+
print(sl.walkway_los(8.5, 600, platoon=True).los) # 'C'
|
|
85
|
+
|
|
86
|
+
# Effective width: 10 ft sidewalk, building facade, no buffer, a light pole
|
|
87
|
+
sl.effective_walkway_width(10, building_edge="building", obstructions=["light_pole"]) # 3.5
|
|
88
|
+
|
|
89
|
+
# Pedestrian segment LOS score for one side of the street
|
|
90
|
+
p = sl.pedestrian_link_score(
|
|
91
|
+
outside_lane_ft=12, bike_lane_ft=5, shoulder_ft=8, parking_occupancy=0.5,
|
|
92
|
+
buffer_ft=4, sidewalk_ft=6, volume_vph=800, through_lanes=2, running_speed_mph=30,
|
|
93
|
+
)
|
|
94
|
+
print(round(p.score, 3), p.los) # 1.997 'A'
|
|
95
|
+
|
|
96
|
+
# Bicycle segment LOS score for one direction
|
|
97
|
+
b = sl.bicycle_link_score(
|
|
98
|
+
outside_lane_ft=12, bike_lane_ft=5, volume_vph=800, through_lanes=2,
|
|
99
|
+
running_speed_mph=35, heavy_vehicle_pct=2, pavement_rating=4,
|
|
100
|
+
)
|
|
101
|
+
print(round(b.score, 3), b.los) # 2.232 'B'
|
|
102
|
+
|
|
103
|
+
# Corner circulation area (time-space)
|
|
104
|
+
c = sl.corner_circulation(10, 12, 15, cycle_s=90, circulating_peds_per_cycle=120,
|
|
105
|
+
waiting=[(20, 60), (25, 55)])
|
|
106
|
+
print(round(c.space_ft2_p, 2), c.los) # 4.9 'F'
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
### Command line
|
|
110
|
+
|
|
111
|
+
```bash
|
|
112
|
+
streetlos segments.csv -o segments_los.csv # US units (ft, mph)
|
|
113
|
+
streetlos segments.csv --units si # metres, km/h -> segments_los.csv
|
|
114
|
+
streetlos segments.csv --platoon # platoon-adjusted walkway criteria
|
|
115
|
+
streetlos segments.csv --tables my_tables.json # override breakpoints
|
|
116
|
+
streetlos --list-tables # print tables and sources
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
One row per segment side (pedestrian) or direction (bicycle). Recognised columns
|
|
120
|
+
(all optional; a model runs only when its inputs are present, and `notes` says
|
|
121
|
+
what was skipped):
|
|
122
|
+
|
|
123
|
+
| column | meaning | unit (us / si) |
|
|
124
|
+
|---|---|---|
|
|
125
|
+
| `segment_id` | identifier, copied through | |
|
|
126
|
+
| `outside_lane` | outside through lane width | ft / m |
|
|
127
|
+
| `bike_lane` | bicycle lane width | ft / m |
|
|
128
|
+
| `shoulder` | paved shoulder or parking lane width | ft / m |
|
|
129
|
+
| `curb` | curb present (yes/no, default yes) | |
|
|
130
|
+
| `parking_occupancy` | share of on-street parking occupied, 0-1 | |
|
|
131
|
+
| `parking_striped` | parking spaces striped (yes/no) | |
|
|
132
|
+
| `buffer` | buffer between sidewalk and road | ft / m |
|
|
133
|
+
| `barrier` | continuous barrier at least 3 ft high in the buffer | |
|
|
134
|
+
| `sidewalk_width` | sidewalk width, excluding the buffer | ft / m |
|
|
135
|
+
| `building_edge` | `none`, `building`, `window_display`, `fence`, `low_wall` | |
|
|
136
|
+
| `obstructions` | `;`-separated names or widths in the walking path | ft / m |
|
|
137
|
+
| `volume_vph` | motor vehicle flow in this direction | veh/h |
|
|
138
|
+
| `through_lanes` | through lanes in this direction | |
|
|
139
|
+
| `speed` | motor vehicle running speed | mph / km/h |
|
|
140
|
+
| `heavy_vehicle_pct` | heavy vehicles | % |
|
|
141
|
+
| `pavement_rating` | pavement condition, 0.5-5 (default 4) | |
|
|
142
|
+
| `divided` | divided street (yes/no) | |
|
|
143
|
+
| `ped_volume_15min` / `ped_volume_hour` + `phf` | two-way pedestrian volume | p |
|
|
144
|
+
| `walk_speed` | walking speed (default 4.4 ft/s) | ft/s / m/s |
|
|
145
|
+
| `facility` | `none`, `shared`, `bike_lane`, `buffered_lane`, `separated`, `path` | |
|
|
146
|
+
| `bike_buffer` | buffer beside the bike lane | ft / m |
|
|
147
|
+
|
|
148
|
+
Output columns: effective width, unit flow, space per pedestrian, walkway LOS
|
|
149
|
+
(space, flow, overall), pedestrian score and LOS, bicycle score and LOS,
|
|
150
|
+
`ped_flags`, `bike_flags`, `notes`. See `examples/segments.csv`.
|
|
151
|
+
|
|
152
|
+
Override file format (`--tables`): `{"walkway_flow": [5, 7, 10, 15, 23]}`, i.e.
|
|
153
|
+
five A-E breakpoints per table name (`streetlos --list-tables` shows the names).
|
|
154
|
+
|
|
155
|
+
---
|
|
156
|
+
|
|
157
|
+
## API overview
|
|
158
|
+
|
|
159
|
+
| function | purpose |
|
|
160
|
+
|---|---|
|
|
161
|
+
| `walkway_los(width, peds_15min, platoon=False)` | walkway LOS by space and flow; worse governs |
|
|
162
|
+
| `effective_walkway_width(total, building_edge, has_buffer, obstructions)` | effective width W_E |
|
|
163
|
+
| `unit_flow_rate`, `pedestrian_space` | v_p = v15 / (15 W_E); A_p = 60 S_p / v_p |
|
|
164
|
+
| `corner_circulation`, `crosswalk_circulation` | time-space circulation area per pedestrian |
|
|
165
|
+
| `pedestrian_link_score(...)` | NCHRP 616 / HCM 2010 pedestrian link score, factors and LOS |
|
|
166
|
+
| `bicycle_link_score(...)` | NCHRP 616 / HCM 2010 bicycle link score, factors and LOS |
|
|
167
|
+
| `pedestrian_comfort`, `bicycle_facility` | screening indicators and flags (`ComfortThresholds`) |
|
|
168
|
+
| `evaluate_segment`, `evaluate_rows`, `evaluate_csv` | batch evaluation of segment tables |
|
|
169
|
+
| `LosTable`, `DEFAULT_TABLES`, `tables_with_overrides` | inspect and replace thresholds |
|
|
170
|
+
|
|
171
|
+
All functions take US customary units (ft, mph, veh/h), because that is how the
|
|
172
|
+
models were calibrated. `streetlos.units` converts from SI.
|
|
173
|
+
|
|
174
|
+
---
|
|
175
|
+
|
|
176
|
+
## Method and sources
|
|
177
|
+
|
|
178
|
+
### Walkway LOS
|
|
179
|
+
Unit flow `v_p = v_15 / (15 W_E)` (p/min/ft) and space `A_p = 60 S_p / v_p`
|
|
180
|
+
(ft²/p), where `S_p` defaults to 4.4 ft/s (3.3 ft/s where more than 20 % of
|
|
181
|
+
pedestrians are elderly). Breakpoints:
|
|
182
|
+
|
|
183
|
+
| LOS | space, ft²/p | flow, p/min/ft | platoon space | platoon flow |
|
|
184
|
+
|---|---|---|---|---|
|
|
185
|
+
| A | > 60 | ≤ 5 | > 530 | ≤ 0.5 |
|
|
186
|
+
| B | > 40 | ≤ 7 | > 90 | ≤ 3 |
|
|
187
|
+
| C | > 24 | ≤ 10 | > 40 | ≤ 6 |
|
|
188
|
+
| D | > 15 | ≤ 15 | > 23 | ≤ 11 |
|
|
189
|
+
| E | > 8 | ≤ 23 | > 11 | ≤ 18 |
|
|
190
|
+
| F | ≤ 8 | > 23 | ≤ 11 | > 18 |
|
|
191
|
+
|
|
192
|
+
Sources: Rouphail et al. (1998) FHWA-RD-98-107, Tables 4 and 6 (adopted in HCM
|
|
193
|
+
2000); NYC Department of City Planning (2006), *Pedestrian Level of Service
|
|
194
|
+
Study, Phase I*, Tables 2.1-2.2. The original platoon research is Pushkarev &
|
|
195
|
+
Zupan (1975), *Urban Space for Pedestrians*.
|
|
196
|
+
|
|
197
|
+
### Effective width
|
|
198
|
+
Building-side shy distance (3 ft window display, 2 ft building facade, 1.5 ft
|
|
199
|
+
fence or low wall), 1.5 ft curb shy distance where there is no buffer, and the
|
|
200
|
+
effective width of obstructions in the walking path (HCM 6th edition values as
|
|
201
|
+
reported by McTrans). The default street-furniture widths are **not verified**
|
|
202
|
+
(see Limitations); measure them or pass numbers.
|
|
203
|
+
|
|
204
|
+
### Corners and crosswalks (time-space)
|
|
205
|
+
Fruin's time-space concept as used by the HCM: available time-space
|
|
206
|
+
(area × cycle) minus the time-space held by waiting pedestrians, divided by the
|
|
207
|
+
pedestrian occupancy time. The corner area loses `(1 − π/4) R² ≈ 0.215 R²` to
|
|
208
|
+
the curb return; waiting time per cycle for uniform arrivals is `N r² / (2C)`;
|
|
209
|
+
circulation time is the HCM constant of 4 s per pedestrian, or Fruin, Ketcham
|
|
210
|
+
and Hecht's `0.12 (W_a + W_b) + 1.4` s (`fruin_circulation_time`). See
|
|
211
|
+
FHWA-RD-98-107 Section 4.
|
|
212
|
+
|
|
213
|
+
### Pedestrian segment (link) LOS score
|
|
214
|
+
`I_p = 6.0468 + F_w + F_v + F_s`, with
|
|
215
|
+
`F_w = −1.2276 ln(W_v + 0.5 W_1 + 50 p_pk + W_buf f_b + W_aA f_sw)`,
|
|
216
|
+
`F_v = 0.0091 v_m / (4 N_th)` and `F_s = 4 (S_R/100)²`, plus the HCM 2010
|
|
217
|
+
width adjustments (`f_b = 5.37` with a continuous barrier, `f_sw = 6.0 − 0.3 W_aA`,
|
|
218
|
+
`W_aA ≤ 10 ft`, volume-adjusted `W_v`, parking-dependent `W_1`). If a pedestrian
|
|
219
|
+
space is known, the reported LOS is the worse of the score LOS and the space LOS.
|
|
220
|
+
|
|
221
|
+
### Bicycle segment (link) LOS score
|
|
222
|
+
`I_b = 0.760 + F_w + F_v + F_s + F_p`, with `F_w = −0.005 W_e²`,
|
|
223
|
+
`F_v = 0.507 ln(v_ma / (4 N_th))`,
|
|
224
|
+
`F_s = 0.199 [1.1199 ln(S_Ra − 20) + 0.8103] (1 + 0.1038 P_HVa)²` and
|
|
225
|
+
`F_p = 7.066 / P_c²`, plus the adjustments `S_Ra ≥ 21 mph`, `v_ma ≥ 4 N_th`
|
|
226
|
+
and the 50 % heavy-vehicle cap at low volumes.
|
|
227
|
+
|
|
228
|
+
Score letters (both models): A ≤ 2.00, B ≤ 2.75, C ≤ 3.50, D ≤ 4.25, E ≤ 5.00, F > 5.00.
|
|
229
|
+
|
|
230
|
+
Sources: Dowling et al. (2008), *Multimodal Level of Service Analysis for Urban
|
|
231
|
+
Streets*, NCHRP Report 616 (note its published erratum for the pedestrian
|
|
232
|
+
segment equation); HCM 2010 Chapter 17, checked against the open restatement in
|
|
233
|
+
Lewis Center for Regional Policy Studies, UCLA (2014), *HCM Bicycle and
|
|
234
|
+
Pedestrian Level of Service: The Ultimate White Paper*. The models descend from
|
|
235
|
+
Landis et al. (1997, TRR 1578) and Landis et al. (2001, TRR 1773).
|
|
236
|
+
|
|
237
|
+
### Comfort indicators
|
|
238
|
+
Clear width is checked against the 4.0 ft (1.2 m) minimum and 5.0 ft passing
|
|
239
|
+
width of the US Access Board's Public Right-of-Way Accessibility Guidelines
|
|
240
|
+
(36 CFR Part 1190, R302.3-R302.4). The other flags (speed above 30 mph without a
|
|
241
|
+
buffer, more than 600 veh/h per lane, bike lane narrower than 5 ft, mixed
|
|
242
|
+
traffic above 25 mph, unbuffered bike lane next to parking) are **screening
|
|
243
|
+
heuristics** with defaults you set through `ComfortThresholds`.
|
|
244
|
+
|
|
245
|
+
### Related package
|
|
246
|
+
For **Bicycle Level of Traffic Stress** (LTS 1-4, Mekuria, Furth & Nixon 2012)
|
|
247
|
+
use [`bikelts`](https://pypi.org/project/bikelts/). `streetlos` gives the
|
|
248
|
+
perception-based LOS scores and walking measures; `bikelts` gives the stress
|
|
249
|
+
classification and low-stress connectivity.
|
|
250
|
+
|
|
251
|
+
---
|
|
252
|
+
|
|
253
|
+
## Limitations
|
|
254
|
+
|
|
255
|
+
- **Screening, not a full HCM analysis.** Intersection LOS, mid-segment
|
|
256
|
+
crossing difficulty, pedestrian delay and facility (multi-segment) aggregation
|
|
257
|
+
are not implemented.
|
|
258
|
+
- The segment models were calibrated on US urban streets, in US units. Results
|
|
259
|
+
elsewhere (for example in Türkiye) indicate relative quality; they are not
|
|
260
|
+
calibrated perceptions.
|
|
261
|
+
- The HCM 2010 bicycle width rule counts the bike lane and shoulder twice when
|
|
262
|
+
their combined width is at least 4 ft (as restated by the Lewis Center paper).
|
|
263
|
+
It is implemented as published. Wide, low-volume cross sections can give
|
|
264
|
+
negative scores, which map to LOS A.
|
|
265
|
+
- Walking speed is taken as constant; the speed-flow reduction of newer HCM
|
|
266
|
+
editions is not applied. Pass `walk_speed_ft_s` if you have a measured speed.
|
|
267
|
+
- **Not verified from an open source:** the street-furniture effective widths
|
|
268
|
+
in `walkway.OBSTRUCTION_WIDTH_FT` (midpoints recalled from the HCM 2000
|
|
269
|
+
fixed-object table), and the use of walkway space breakpoints for corner and
|
|
270
|
+
crosswalk circulation area (`CORNER_CROSSWALK_SPACE`, flagged `verified=False`).
|
|
271
|
+
- Comfort thresholds other than the PROWAG widths are heuristics.
|
|
272
|
+
|
|
273
|
+
---
|
|
274
|
+
|
|
275
|
+
## Development
|
|
276
|
+
|
|
277
|
+
```bash
|
|
278
|
+
pip install -e ".[dev]"
|
|
279
|
+
python -m pytest
|
|
280
|
+
python -m ruff check . && python -m ruff format --check src tests
|
|
281
|
+
python -m mypy src
|
|
282
|
+
```
|
|
283
|
+
|
|
284
|
+
## Academic citation
|
|
285
|
+
|
|
286
|
+
```bibtex
|
|
287
|
+
@software{eminoglu_streetlos,
|
|
288
|
+
author = {Eminoğlu, Yusuf},
|
|
289
|
+
title = {streetlos},
|
|
290
|
+
year = {2026},
|
|
291
|
+
version = {0.1.0},
|
|
292
|
+
url = {https://gitlab.com/geophilo1/streetlos_sdk}
|
|
293
|
+
}
|
|
294
|
+
```
|
|
295
|
+
|
|
296
|
+
## License
|
|
297
|
+
|
|
298
|
+
MIT © 2026 Yusuf Eminoğlu. Contact: geospacephilo@gmail.com
|
|
@@ -0,0 +1,263 @@
|
|
|
1
|
+
# streetlos
|
|
2
|
+
|
|
3
|
+
[](https://pypi.org/project/streetlos/)
|
|
4
|
+
[](https://pypi.org/project/streetlos/)
|
|
5
|
+
[](https://gitlab.com/geophilo1/streetlos_sdk/-/pipelines)
|
|
6
|
+
[](https://gitlab.com/geophilo1/streetlos_sdk/-/blob/main/LICENSE)
|
|
7
|
+
|
|
8
|
+
**Multimodal street level-of-service screening for walking and cycling.**
|
|
9
|
+
|
|
10
|
+
`streetlos` scores street segments for pedestrians and cyclists from a plain CSV
|
|
11
|
+
of street attributes. It is written for planners and researchers who need a
|
|
12
|
+
transparent, reproducible screening (which streets look poor, and why) rather
|
|
13
|
+
than a black box. Every threshold table is cited and can be overridden.
|
|
14
|
+
|
|
15
|
+
- **Walkway LOS** by space per pedestrian and unit flow rate, with the
|
|
16
|
+
average-flow and the **platoon-adjusted** criteria.
|
|
17
|
+
- **Effective sidewalk width** after shy distances and street furniture.
|
|
18
|
+
- **Corner and crosswalk circulation area** with the time-space method.
|
|
19
|
+
- **Pedestrian and bicycle segment LOS scores** from NCHRP Report 616
|
|
20
|
+
(Dowling et al. 2008), in the form adopted by HCM 2010.
|
|
21
|
+
- **Comfort indicators**: clear width against the PROWAG minimum, buffer,
|
|
22
|
+
traffic speed and volume per lane, bike lane width and door-zone exposure.
|
|
23
|
+
- **CLI**: CSV of segments in, LOS table out. US (ft, mph) or SI (m, km/h) units.
|
|
24
|
+
|
|
25
|
+
No runtime dependencies: the standard library is enough.
|
|
26
|
+
|
|
27
|
+
```bash
|
|
28
|
+
pip install streetlos
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
Requires Python 3.9 or newer.
|
|
32
|
+
|
|
33
|
+
> **About the HCM.** The *Highway Capacity Manual* is a copyrighted publication
|
|
34
|
+
> of the Transportation Research Board. `streetlos` does not reproduce its text.
|
|
35
|
+
> It implements published equations and numeric thresholds, cites the openly
|
|
36
|
+
> accessible documents they were checked against, and lets you replace every
|
|
37
|
+
> table (for example with the values of the HCM edition your agency uses).
|
|
38
|
+
|
|
39
|
+
---
|
|
40
|
+
|
|
41
|
+
## Quickstart
|
|
42
|
+
|
|
43
|
+
```python
|
|
44
|
+
import streetlos as sl
|
|
45
|
+
|
|
46
|
+
# Walkway: 8.5 ft effective width, 600 pedestrians in the peak 15 minutes
|
|
47
|
+
w = sl.walkway_los(8.5, 600)
|
|
48
|
+
print(w.unit_flow_p_min_ft, w.space_ft2_p, w.los) # 4.71 56.1 'B'
|
|
49
|
+
print(sl.walkway_los(8.5, 600, platoon=True).los) # 'C'
|
|
50
|
+
|
|
51
|
+
# Effective width: 10 ft sidewalk, building facade, no buffer, a light pole
|
|
52
|
+
sl.effective_walkway_width(10, building_edge="building", obstructions=["light_pole"]) # 3.5
|
|
53
|
+
|
|
54
|
+
# Pedestrian segment LOS score for one side of the street
|
|
55
|
+
p = sl.pedestrian_link_score(
|
|
56
|
+
outside_lane_ft=12, bike_lane_ft=5, shoulder_ft=8, parking_occupancy=0.5,
|
|
57
|
+
buffer_ft=4, sidewalk_ft=6, volume_vph=800, through_lanes=2, running_speed_mph=30,
|
|
58
|
+
)
|
|
59
|
+
print(round(p.score, 3), p.los) # 1.997 'A'
|
|
60
|
+
|
|
61
|
+
# Bicycle segment LOS score for one direction
|
|
62
|
+
b = sl.bicycle_link_score(
|
|
63
|
+
outside_lane_ft=12, bike_lane_ft=5, volume_vph=800, through_lanes=2,
|
|
64
|
+
running_speed_mph=35, heavy_vehicle_pct=2, pavement_rating=4,
|
|
65
|
+
)
|
|
66
|
+
print(round(b.score, 3), b.los) # 2.232 'B'
|
|
67
|
+
|
|
68
|
+
# Corner circulation area (time-space)
|
|
69
|
+
c = sl.corner_circulation(10, 12, 15, cycle_s=90, circulating_peds_per_cycle=120,
|
|
70
|
+
waiting=[(20, 60), (25, 55)])
|
|
71
|
+
print(round(c.space_ft2_p, 2), c.los) # 4.9 'F'
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
### Command line
|
|
75
|
+
|
|
76
|
+
```bash
|
|
77
|
+
streetlos segments.csv -o segments_los.csv # US units (ft, mph)
|
|
78
|
+
streetlos segments.csv --units si # metres, km/h -> segments_los.csv
|
|
79
|
+
streetlos segments.csv --platoon # platoon-adjusted walkway criteria
|
|
80
|
+
streetlos segments.csv --tables my_tables.json # override breakpoints
|
|
81
|
+
streetlos --list-tables # print tables and sources
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
One row per segment side (pedestrian) or direction (bicycle). Recognised columns
|
|
85
|
+
(all optional; a model runs only when its inputs are present, and `notes` says
|
|
86
|
+
what was skipped):
|
|
87
|
+
|
|
88
|
+
| column | meaning | unit (us / si) |
|
|
89
|
+
|---|---|---|
|
|
90
|
+
| `segment_id` | identifier, copied through | |
|
|
91
|
+
| `outside_lane` | outside through lane width | ft / m |
|
|
92
|
+
| `bike_lane` | bicycle lane width | ft / m |
|
|
93
|
+
| `shoulder` | paved shoulder or parking lane width | ft / m |
|
|
94
|
+
| `curb` | curb present (yes/no, default yes) | |
|
|
95
|
+
| `parking_occupancy` | share of on-street parking occupied, 0-1 | |
|
|
96
|
+
| `parking_striped` | parking spaces striped (yes/no) | |
|
|
97
|
+
| `buffer` | buffer between sidewalk and road | ft / m |
|
|
98
|
+
| `barrier` | continuous barrier at least 3 ft high in the buffer | |
|
|
99
|
+
| `sidewalk_width` | sidewalk width, excluding the buffer | ft / m |
|
|
100
|
+
| `building_edge` | `none`, `building`, `window_display`, `fence`, `low_wall` | |
|
|
101
|
+
| `obstructions` | `;`-separated names or widths in the walking path | ft / m |
|
|
102
|
+
| `volume_vph` | motor vehicle flow in this direction | veh/h |
|
|
103
|
+
| `through_lanes` | through lanes in this direction | |
|
|
104
|
+
| `speed` | motor vehicle running speed | mph / km/h |
|
|
105
|
+
| `heavy_vehicle_pct` | heavy vehicles | % |
|
|
106
|
+
| `pavement_rating` | pavement condition, 0.5-5 (default 4) | |
|
|
107
|
+
| `divided` | divided street (yes/no) | |
|
|
108
|
+
| `ped_volume_15min` / `ped_volume_hour` + `phf` | two-way pedestrian volume | p |
|
|
109
|
+
| `walk_speed` | walking speed (default 4.4 ft/s) | ft/s / m/s |
|
|
110
|
+
| `facility` | `none`, `shared`, `bike_lane`, `buffered_lane`, `separated`, `path` | |
|
|
111
|
+
| `bike_buffer` | buffer beside the bike lane | ft / m |
|
|
112
|
+
|
|
113
|
+
Output columns: effective width, unit flow, space per pedestrian, walkway LOS
|
|
114
|
+
(space, flow, overall), pedestrian score and LOS, bicycle score and LOS,
|
|
115
|
+
`ped_flags`, `bike_flags`, `notes`. See `examples/segments.csv`.
|
|
116
|
+
|
|
117
|
+
Override file format (`--tables`): `{"walkway_flow": [5, 7, 10, 15, 23]}`, i.e.
|
|
118
|
+
five A-E breakpoints per table name (`streetlos --list-tables` shows the names).
|
|
119
|
+
|
|
120
|
+
---
|
|
121
|
+
|
|
122
|
+
## API overview
|
|
123
|
+
|
|
124
|
+
| function | purpose |
|
|
125
|
+
|---|---|
|
|
126
|
+
| `walkway_los(width, peds_15min, platoon=False)` | walkway LOS by space and flow; worse governs |
|
|
127
|
+
| `effective_walkway_width(total, building_edge, has_buffer, obstructions)` | effective width W_E |
|
|
128
|
+
| `unit_flow_rate`, `pedestrian_space` | v_p = v15 / (15 W_E); A_p = 60 S_p / v_p |
|
|
129
|
+
| `corner_circulation`, `crosswalk_circulation` | time-space circulation area per pedestrian |
|
|
130
|
+
| `pedestrian_link_score(...)` | NCHRP 616 / HCM 2010 pedestrian link score, factors and LOS |
|
|
131
|
+
| `bicycle_link_score(...)` | NCHRP 616 / HCM 2010 bicycle link score, factors and LOS |
|
|
132
|
+
| `pedestrian_comfort`, `bicycle_facility` | screening indicators and flags (`ComfortThresholds`) |
|
|
133
|
+
| `evaluate_segment`, `evaluate_rows`, `evaluate_csv` | batch evaluation of segment tables |
|
|
134
|
+
| `LosTable`, `DEFAULT_TABLES`, `tables_with_overrides` | inspect and replace thresholds |
|
|
135
|
+
|
|
136
|
+
All functions take US customary units (ft, mph, veh/h), because that is how the
|
|
137
|
+
models were calibrated. `streetlos.units` converts from SI.
|
|
138
|
+
|
|
139
|
+
---
|
|
140
|
+
|
|
141
|
+
## Method and sources
|
|
142
|
+
|
|
143
|
+
### Walkway LOS
|
|
144
|
+
Unit flow `v_p = v_15 / (15 W_E)` (p/min/ft) and space `A_p = 60 S_p / v_p`
|
|
145
|
+
(ft²/p), where `S_p` defaults to 4.4 ft/s (3.3 ft/s where more than 20 % of
|
|
146
|
+
pedestrians are elderly). Breakpoints:
|
|
147
|
+
|
|
148
|
+
| LOS | space, ft²/p | flow, p/min/ft | platoon space | platoon flow |
|
|
149
|
+
|---|---|---|---|---|
|
|
150
|
+
| A | > 60 | ≤ 5 | > 530 | ≤ 0.5 |
|
|
151
|
+
| B | > 40 | ≤ 7 | > 90 | ≤ 3 |
|
|
152
|
+
| C | > 24 | ≤ 10 | > 40 | ≤ 6 |
|
|
153
|
+
| D | > 15 | ≤ 15 | > 23 | ≤ 11 |
|
|
154
|
+
| E | > 8 | ≤ 23 | > 11 | ≤ 18 |
|
|
155
|
+
| F | ≤ 8 | > 23 | ≤ 11 | > 18 |
|
|
156
|
+
|
|
157
|
+
Sources: Rouphail et al. (1998) FHWA-RD-98-107, Tables 4 and 6 (adopted in HCM
|
|
158
|
+
2000); NYC Department of City Planning (2006), *Pedestrian Level of Service
|
|
159
|
+
Study, Phase I*, Tables 2.1-2.2. The original platoon research is Pushkarev &
|
|
160
|
+
Zupan (1975), *Urban Space for Pedestrians*.
|
|
161
|
+
|
|
162
|
+
### Effective width
|
|
163
|
+
Building-side shy distance (3 ft window display, 2 ft building facade, 1.5 ft
|
|
164
|
+
fence or low wall), 1.5 ft curb shy distance where there is no buffer, and the
|
|
165
|
+
effective width of obstructions in the walking path (HCM 6th edition values as
|
|
166
|
+
reported by McTrans). The default street-furniture widths are **not verified**
|
|
167
|
+
(see Limitations); measure them or pass numbers.
|
|
168
|
+
|
|
169
|
+
### Corners and crosswalks (time-space)
|
|
170
|
+
Fruin's time-space concept as used by the HCM: available time-space
|
|
171
|
+
(area × cycle) minus the time-space held by waiting pedestrians, divided by the
|
|
172
|
+
pedestrian occupancy time. The corner area loses `(1 − π/4) R² ≈ 0.215 R²` to
|
|
173
|
+
the curb return; waiting time per cycle for uniform arrivals is `N r² / (2C)`;
|
|
174
|
+
circulation time is the HCM constant of 4 s per pedestrian, or Fruin, Ketcham
|
|
175
|
+
and Hecht's `0.12 (W_a + W_b) + 1.4` s (`fruin_circulation_time`). See
|
|
176
|
+
FHWA-RD-98-107 Section 4.
|
|
177
|
+
|
|
178
|
+
### Pedestrian segment (link) LOS score
|
|
179
|
+
`I_p = 6.0468 + F_w + F_v + F_s`, with
|
|
180
|
+
`F_w = −1.2276 ln(W_v + 0.5 W_1 + 50 p_pk + W_buf f_b + W_aA f_sw)`,
|
|
181
|
+
`F_v = 0.0091 v_m / (4 N_th)` and `F_s = 4 (S_R/100)²`, plus the HCM 2010
|
|
182
|
+
width adjustments (`f_b = 5.37` with a continuous barrier, `f_sw = 6.0 − 0.3 W_aA`,
|
|
183
|
+
`W_aA ≤ 10 ft`, volume-adjusted `W_v`, parking-dependent `W_1`). If a pedestrian
|
|
184
|
+
space is known, the reported LOS is the worse of the score LOS and the space LOS.
|
|
185
|
+
|
|
186
|
+
### Bicycle segment (link) LOS score
|
|
187
|
+
`I_b = 0.760 + F_w + F_v + F_s + F_p`, with `F_w = −0.005 W_e²`,
|
|
188
|
+
`F_v = 0.507 ln(v_ma / (4 N_th))`,
|
|
189
|
+
`F_s = 0.199 [1.1199 ln(S_Ra − 20) + 0.8103] (1 + 0.1038 P_HVa)²` and
|
|
190
|
+
`F_p = 7.066 / P_c²`, plus the adjustments `S_Ra ≥ 21 mph`, `v_ma ≥ 4 N_th`
|
|
191
|
+
and the 50 % heavy-vehicle cap at low volumes.
|
|
192
|
+
|
|
193
|
+
Score letters (both models): A ≤ 2.00, B ≤ 2.75, C ≤ 3.50, D ≤ 4.25, E ≤ 5.00, F > 5.00.
|
|
194
|
+
|
|
195
|
+
Sources: Dowling et al. (2008), *Multimodal Level of Service Analysis for Urban
|
|
196
|
+
Streets*, NCHRP Report 616 (note its published erratum for the pedestrian
|
|
197
|
+
segment equation); HCM 2010 Chapter 17, checked against the open restatement in
|
|
198
|
+
Lewis Center for Regional Policy Studies, UCLA (2014), *HCM Bicycle and
|
|
199
|
+
Pedestrian Level of Service: The Ultimate White Paper*. The models descend from
|
|
200
|
+
Landis et al. (1997, TRR 1578) and Landis et al. (2001, TRR 1773).
|
|
201
|
+
|
|
202
|
+
### Comfort indicators
|
|
203
|
+
Clear width is checked against the 4.0 ft (1.2 m) minimum and 5.0 ft passing
|
|
204
|
+
width of the US Access Board's Public Right-of-Way Accessibility Guidelines
|
|
205
|
+
(36 CFR Part 1190, R302.3-R302.4). The other flags (speed above 30 mph without a
|
|
206
|
+
buffer, more than 600 veh/h per lane, bike lane narrower than 5 ft, mixed
|
|
207
|
+
traffic above 25 mph, unbuffered bike lane next to parking) are **screening
|
|
208
|
+
heuristics** with defaults you set through `ComfortThresholds`.
|
|
209
|
+
|
|
210
|
+
### Related package
|
|
211
|
+
For **Bicycle Level of Traffic Stress** (LTS 1-4, Mekuria, Furth & Nixon 2012)
|
|
212
|
+
use [`bikelts`](https://pypi.org/project/bikelts/). `streetlos` gives the
|
|
213
|
+
perception-based LOS scores and walking measures; `bikelts` gives the stress
|
|
214
|
+
classification and low-stress connectivity.
|
|
215
|
+
|
|
216
|
+
---
|
|
217
|
+
|
|
218
|
+
## Limitations
|
|
219
|
+
|
|
220
|
+
- **Screening, not a full HCM analysis.** Intersection LOS, mid-segment
|
|
221
|
+
crossing difficulty, pedestrian delay and facility (multi-segment) aggregation
|
|
222
|
+
are not implemented.
|
|
223
|
+
- The segment models were calibrated on US urban streets, in US units. Results
|
|
224
|
+
elsewhere (for example in Türkiye) indicate relative quality; they are not
|
|
225
|
+
calibrated perceptions.
|
|
226
|
+
- The HCM 2010 bicycle width rule counts the bike lane and shoulder twice when
|
|
227
|
+
their combined width is at least 4 ft (as restated by the Lewis Center paper).
|
|
228
|
+
It is implemented as published. Wide, low-volume cross sections can give
|
|
229
|
+
negative scores, which map to LOS A.
|
|
230
|
+
- Walking speed is taken as constant; the speed-flow reduction of newer HCM
|
|
231
|
+
editions is not applied. Pass `walk_speed_ft_s` if you have a measured speed.
|
|
232
|
+
- **Not verified from an open source:** the street-furniture effective widths
|
|
233
|
+
in `walkway.OBSTRUCTION_WIDTH_FT` (midpoints recalled from the HCM 2000
|
|
234
|
+
fixed-object table), and the use of walkway space breakpoints for corner and
|
|
235
|
+
crosswalk circulation area (`CORNER_CROSSWALK_SPACE`, flagged `verified=False`).
|
|
236
|
+
- Comfort thresholds other than the PROWAG widths are heuristics.
|
|
237
|
+
|
|
238
|
+
---
|
|
239
|
+
|
|
240
|
+
## Development
|
|
241
|
+
|
|
242
|
+
```bash
|
|
243
|
+
pip install -e ".[dev]"
|
|
244
|
+
python -m pytest
|
|
245
|
+
python -m ruff check . && python -m ruff format --check src tests
|
|
246
|
+
python -m mypy src
|
|
247
|
+
```
|
|
248
|
+
|
|
249
|
+
## Academic citation
|
|
250
|
+
|
|
251
|
+
```bibtex
|
|
252
|
+
@software{eminoglu_streetlos,
|
|
253
|
+
author = {Eminoğlu, Yusuf},
|
|
254
|
+
title = {streetlos},
|
|
255
|
+
year = {2026},
|
|
256
|
+
version = {0.1.0},
|
|
257
|
+
url = {https://gitlab.com/geophilo1/streetlos_sdk}
|
|
258
|
+
}
|
|
259
|
+
```
|
|
260
|
+
|
|
261
|
+
## License
|
|
262
|
+
|
|
263
|
+
MIT © 2026 Yusuf Eminoğlu. Contact: geospacephilo@gmail.com
|