Temporal networks¶
Build snapshots from the dates in a processed OD table, with a shared node
order. For downloaded data, provide the acquisition manifest from
get_acquisition_manifest().
The examples show how source coverage changes the mean.
snapshot()builds a network for one observed day.sum_network()sums selected observed days.mean_per_observed_day()divides by the number of selected observed days, including genuinely observed days with no retained flows.coverageidentifies observed, missing and unresolved dates.Snapshot comparison methods use the same measures as Flow measures and comparisons.
Build temporal networks¶
- pyspainmobility.network.temporal.build_temporal_network(data: str | Path | DataFrame | DataFrame | LazyFrame, *, spec: NetworkSpec | None = None, time_column: str = 'date', requested_dates: Sequence[object] | None = None, observed_dates: Sequence[object] | None = None, acquisition_manifest: DataFrame | DataFrame | None = None, manifest_date_column: str = 'date', manifest_status_column: str = 'status', node_ids: Sequence[object] | None = None, node_index: NodeIndex | None = None, max_cached_snapshots: int | None = 32, failed_data_policy: Literal['error', 'exclude'] = 'error') TemporalMobilityNetwork[source]¶
Build daily networks with a shared node order and explicit source coverage.
- Parameters:
data (str, pathlib.Path, pandas.DataFrame, polars.DataFrame or polars.LazyFrame) – Processed OD rows or a Parquet file/dataset directory.
spec (NetworkSpec, optional) – Weight column and self-loop policy, as in
build_network().time_column (str) – Column identifying the observation date. Default is
'date'.requested_dates (sequence, optional) – Dates to analyse, including any requested days that may be missing. Must contain at least one date when provided.
observed_dates (sequence, optional) – Dates of successfully observed source days, including known empty days. Use either this argument or
acquisition_manifest.acquisition_manifest (pandas.DataFrame or polars.DataFrame, optional) – Source-day record from
Mobility.get_acquisition_manifest(). Failed source days are excluded from observed coverage.manifest_date_column (str) – Manifest columns. Defaults are
'date'and'status'.manifest_status_column (str) – Manifest columns. Defaults are
'date'and'status'.node_ids (sequence, optional) – Complete, ordered node universe, including isolates.
node_index (NodeIndex, optional) – Shared node order and zoning identity; cannot be combined with
node_ids.max_cached_snapshots (int or None) – Maximum snapshots retained in memory. Default is 32; 0 disables caching, and None leaves the cache unbounded.
failed_data_policy ({'error', 'exclude'}) – Raise if OD rows belong to failed source days, or explicitly remove all such rows. Default is
'error'.
- Returns:
Daily snapshots, sums and means over observed days, with source coverage in
coverage. Snapshot matrices are built only when requested.- Return type:
Notes
observed_datesis deliberately separate from OD rows. Pass the dates of source files successfully obtained/parsed to correctly represent an observed day with zero OD rows. Preferacquisition_manifestfromMobility.get_acquisition_manifest(): it also records failed and empty source files before OD filtering. If both are omitted, source coverage is inferred from data rows and requested-but-empty dates stay unresolved.datamay be a Hive-partitioned Parquet directory such asdate=2024-01-01/part-0.parquet. The partition column is available astime_columnand date filters retain Polars partition pruning. By default at most 32 snapshot matrices are retained; passNonefor an unbounded cache or0to disable snapshot caching.If a source manifest marks a day as failed but the OD table still contains its rows, the default
failed_data_policy='error'stops the pipeline: a partial day must never enter an observed-day average. Pass'exclude'to deliberately remove every row for such failed dates.Examples
>>> import polars as pl >>> from pyspainmobility import build_temporal_network >>> od = pl.DataFrame({ ... "date": ["2024-01-01", "2024-01-03"], ... "id_origin": ["A", "A"], "id_destination": ["B", "B"], ... "n_trips": [3.0, 5.0], ... }) >>> temporal = build_temporal_network( ... od, observed_dates=["2024-01-01", "2024-01-03"], ... ) >>> temporal.snapshot("2024-01-01").total_weight 3.0 >>> temporal.mean_per_observed_day().total_weight 4.0
Snapshots and aggregates¶
Create this result with build_temporal_network().
- class pyspainmobility.network.temporal.TemporalMobilityNetwork(_source: LazyFrame, time_column: str, spec: NetworkSpec, node_ids: ndarray, coverage: TemporalCoverage, max_cached_snapshots: int | None = 32, _cache: OrderedDict[str, ~pyspainmobility.network.model.SparseMobilityNetwork]=<factory>, node_index: NodeIndex | None = None)[source]¶
Lazy snapshots that share one immutable node index.
Snapshot matrices are constructed only when requested. An LRU cache bounds retained CSR matrices while every snapshot uses the same
node_ids, so entries at the same matrix coordinates refer to the same zones.- property number_of_observed_days: int¶
Days known observed in the source, including known empty days.
- snapshot(when: object) SparseMobilityNetwork[source]¶
Return the network for one observed source day.
- Parameters:
when (str or date-like) – Observed date, for example
'2024-01-01'. A missing source day raises.- Returns:
Daily network with the temporal result’s shared node index. Known empty observed days return a zero-flow matrix retaining all nodes.
- Return type:
- snapshots(include_empty: bool = False) Iterator[Tuple[str, SparseMobilityNetwork]][source]¶
Yield snapshots in date order, building each one only on demand.
- sum_network(dates: Sequence[object] | None = None) SparseMobilityNetwork[source]¶
Sum flows across selected observed source dates.
- Parameters:
dates (sequence, optional) – Observed days to sum. None selects all observed source days.
- Returns:
Summed flows with the shared node index and selected dates in the audit.
- Return type:
- mean_per_observed_day(dates: Sequence[object] | None = None) SparseMobilityNetwork[source]¶
Average flows over selected observed source dates.
Known empty observed dates remain in the denominator. A requested date that is missing or failed in the source manifest raises instead of being converted to a zero-flow day.
- Parameters:
dates (sequence, optional) – Observed days to average. None selects all observed source days.
- Returns:
Summed flows divided by the number of selected observed days, with that denominator and the selected dates recorded in the audit.
- Return type:
- snapshot_strengths(when: object) DataFrame[source]¶
Return in/out weighted strength for every node on one observed day.
- compare_snapshots(left: object, right: object) NetworkComparison[source]¶
Compare two observed dates with a shared node-index contract.
- snapshot_edge_changes(left: object, right: object) DataFrame[source]¶
Return the sparse union of directed-edge changes between two dates.
Source coverage¶
- class pyspainmobility.network.temporal.TemporalCoverage(requested_dates: Tuple[str, ...], source_dates: Tuple[str, ...], data_dates: Tuple[str, ...], source_manifest_provided: bool, excluded_data_dates: Tuple[str, ...] = (), excluded_data_weight: float = 0.0, excluded_invalid_row_count: int = 0)[source]¶
Distinguish requested, source-observed, and data-bearing dates.
source_datescomes from a caller-provided source manifest when one is available: for example, the list of downloaded MITMA files that were successfully parsed. It can therefore contain a date with an empty OD file. Without such a manifest it is inferred from OD rows and empty observed days cannot be distinguished from unavailable source days.- property missing_source_dates: Tuple[str, ...]¶
Requested dates known to be absent from the source manifest.
- property empty_observed_dates: Tuple[str, ...]¶
Observed source dates for which the OD table has no rows.