Banner

6.2 Data¶

Part: 6 — Geographically Weighted Models (Chapter 6.2 of 14)

Dataset: diabetes_atlantic.shp (666 counties); data_1998_2010_long_lbc.csv (space-time panel); bundled simulation datasets

Focus: Every dataset used across Part 6, and a clear boundary between real data and API-demonstration data

Library: spatialstats.gwmodel (PySpatialStats)


Table of Contents¶

  1. Overview

  2. Python Setup

  3. The Real Dataset: diabetes_atlantic

  4. The Space-Time Panel

  5. Bundled Simulation Datasets — API Demonstrations Only

  6. Summary and Conclusions

  7. Resources


1. Overview¶

Part 6 uses three distinct kinds of data, and it matters which is which: a real health dataset whose results are genuine findings, a real space-time panel for the spatiotemporal chapters, and four small simulated datasets bundled with the library purely to demonstrate API syntax quickly. Mixing these up — reporting a load_georgia() coefficient as if it were a real Georgia finding — would misrepresent synthetic data as evidence. This chapter draws the line explicitly before any modelling begins.

Step What we do
Real data diabetes_atlantic.shp — the primary dataset for every substantive GWR result in this Part
Panel data_1998_2010_long_lbc.csv — the space-time data GTWR (Chapter 6.10) needs
Simulated The four bundled loaders, explicitly labelled as syntax demonstrations, never as findings

2. Python Setup¶

In [1]:
import sys, warnings
from pathlib import Path

import numpy as np
import pandas as pd
import geopandas as gpd
import matplotlib.pyplot as plt

warnings.filterwarnings("ignore", category=FutureWarning)
warnings.filterwarnings("ignore", category=DeprecationWarning)


def find_repo_root(start: Path = Path.cwd()) -> Path:
    for p in [start, *start.parents]:
        if (p / "pyproject.toml").exists() and (p / "data").is_dir():
            return p
    raise FileNotFoundError("Run this notebook from inside the PySpatialStats repository.")


ROOT = find_repo_root()
DATA = ROOT / "data"
try:
    import spatialstats
except ImportError:
    sys.path.insert(0, str(ROOT))
    import spatialstats

from spatialstats.gwmodel.datasets import load_georgia, load_londonhouse, load_beijing_pm25, load_ncovid

plt.rcParams.update({
    "figure.dpi": 100, "savefig.dpi": 100, "font.size": 10, "axes.titlesize": 11,
    "axes.titleweight": "bold", "axes.spines.top": False, "axes.spines.right": False,
    "axes.grid": True, "grid.alpha": 0.25, "legend.frameon": False,
})
C = {"blue": "#2b6cb0", "red": "#c0392b", "green": "#2f855a", "orange": "#dd6b20",
     "grey": "#718096", "purple": "#6b46c1", "teal": "#2c7a7b"}

print(f"spatialstats : version {spatialstats.__version__}")
spatialstats : version 0.2.0

3. The Real Dataset: diabetes_atlantic¶

The same dataset used throughout Part 3: 666 Atlantic-seaboard counties, Dia_pct explained by six health and access covariates, with centroids x, y already in EPSG:5070 (metres) — the projected CRS every GW model in this library requires, since bandwidths are measured in coordinate units directly.

In [2]:
counties = gpd.read_file(DATA / "diabetes_atlantic.shp")
covariates = ["Obesity", "PhysInact", "Acc_Exer", "PCP_rate", "FoodEnvIdx", "SVI"]
print(f"counties: {counties.shape[0]}, CRS: {counties.crs.to_epsg()} (projected, metres)")
print(f"centroid x range: [{counties['x'].min():,.0f}, {counties['x'].max():,.0f}] m")
print(f"centroid y range: [{counties['y'].min():,.0f}, {counties['y'].max():,.0f}] m")
counties[["COUNTY", "STATE", "Dia_pct"] + covariates].describe().round(2)
counties: 666, CRS: 5070 (projected, metres)
centroid x range: [949,877, 1,916,559] m
centroid y range: [932,261, 2,623,675] m
Out[2]:
Dia_pct Obesity PhysInact Acc_Exer PCP_rate FoodEnvIdx SVI
count 666.00 666.00 666.00 666.00 666.00 666.00 666.00
mean 9.14 27.72 21.54 64.62 55.71 7.54 0.57
std 1.56 4.79 3.78 22.83 38.31 0.98 0.28
min 5.86 16.80 13.28 0.00 5.00 2.60 0.00
25% 7.98 23.56 18.74 50.00 32.80 7.00 0.35
50% 8.88 27.96 21.17 66.40 47.60 7.60 0.57
75% 9.98 31.26 23.83 82.35 70.55 8.20 0.81
max 16.96 41.18 35.16 100.00 536.60 10.00 1.00

Every real GWR result in Chapters 6.4–6.9 and 6.12–6.14 is fit on this exact specification: Dia_pct ~ Obesity + PhysInact + Acc_Exer + PCP_rate + FoodEnvIdx + SVI, the same one used in Part 3, so every comparison against the global OLS/SLM/SEM models (Chapter 6.8) is apples to apples.


4. The Space-Time Panel¶

data_1998_2010_long_lbc.csv — already used in Part 3, Chapter 3.4 for the differential Moran's I example — covers 3,107 US counties from 1998 to 2012 (its filename undersells its own date range) with five environmental/health covariates and a mortality RATE. Chapter 6.10's GTWR needs both space and time coordinates, so this is the only dataset in this Part with a genuine temporal dimension.

In [3]:
panel = pd.read_csv(DATA / "data_1998_2010_long_lbc.csv")
print(f"panel: {panel.shape[0]:,} rows, {panel['FIPS'].nunique():,} counties, "
      f"years {panel['Year'].min()}-{panel['Year'].max()}")
panel.head(3)
panel: 46,605 rows, 3,107 counties, years 1998-2012
Out[3]:
FIPS X Y Year SMOKING POVERTY PM25 NO2 SO2 RATE
0 1001 872679.179 1094432.99 1998 27.0 11.3 17.08 1.38 0.057 90.63
1 1001 872679.179 1094432.99 1999 26.0 11.4 15.38 1.04 0.055 90.39
2 1001 872679.179 1094432.99 2000 26.0 10.5 14.04 1.47 0.054 89.47

For the space-time chapters, this Part uses the same 217 Northeast counties as Parts 2–5 (matched by FIPS), restricted to a handful of years — large enough to show genuine space-time structure, small enough to fit quickly (Chapter 6.12 times this precisely).

In [4]:
northeast = gpd.read_file(DATA / "diabetes_northeast.shp")
fips_ne = set(northeast["FIPS"].astype(int))
panel_ne = panel[panel["FIPS"].isin(fips_ne)]
print(f"Northeast subset: {panel_ne['FIPS'].nunique()} counties x "
      f"{panel_ne['Year'].nunique()} years = {len(panel_ne)} rows")
Northeast subset: 217 counties x 15 years = 3255 rows

5. Bundled Simulation Datasets — API Demonstrations Only¶

spatialstats.gwmodel.datasets bundles four synthetic datasets, generated to exercise specific model shapes (count outcomes, spatial PCA, etc.) quickly without downloading anything. Every result computed from these four loaders in this Part is a syntax demonstration, not a finding — they are used exactly where the outline calls for a quick API illustration (Chapter 6.6's GWGLM count-outcome demo, for instance) and nowhere else.

In [5]:
demo_sets = {
    "load_georgia": load_georgia, "load_londonhouse": load_londonhouse,
    "load_beijing_pm25": load_beijing_pm25, "load_ncovid": load_ncovid,
}
rows = []
for name, loader in demo_sets.items():
    gdf, features, target = loader()
    rows.append({"loader": name, "n": len(gdf), "features": ", ".join(features), "target": target})
pd.DataFrame(rows)
Out[5]:
loader n features target
0 load_georgia 159 PctRural, PctBach, PctEld, PctFB, PctPov, PctB... TotPop90
1 load_londonhouse 500 FloorArea, Bathrooms, Bedrooms, DistCenter, Gr... Price
2 load_beijing_pm25 300 AOD, DEM, Wind, Humidity, Temperature PM25
3 load_ncovid 400 PopDensity, MedianAge, PctUninsured, HospBeds,... MortalityRate

None of these four represent real Georgia counties, real London house prices, real Beijing air quality, or real COVID mortality — they are synthetic data shaped like those domains, useful only for confirming a function call works as documented. Any chapter that uses one says so explicitly in its own text, exactly as this section does.


6. Summary and Conclusions¶

This chapter drew an explicit line between real and synthetic data before any modelling begins.

What we did¶

  1. Confirmed diabetes_atlantic.shp's 666 counties, projected EPSG:5070 CRS, and the exact regression specification every later chapter's real GWR results use.
  2. Confirmed the space-time panel's coverage (3,107 counties, 1998–2012) and built the 217-county Northeast subset Chapter 6.10 uses for GTWR.
  3. Loaded all four bundled simulation datasets and labelled them explicitly as API-demonstration-only data, never to be reported as real findings.

Practical takeaways¶

  • Always check a bundled "example dataset"'s provenance before reporting a result from it — several libraries, this one included, ship synthetic data specifically for fast API demonstrations.
  • Keeping the projected CRS in view (x, y already in metres here) matters immediately: every bandwidth in this Part is a distance or a neighbour count in these exact coordinate units.

Next steps¶

Chapter 6.3 (Kernels, Bandwidths and the Fitting Pattern) builds the full kernel and bandwidth-selection machinery on this chapter's real Atlantic-county data.


7. Resources¶

Textbooks¶

Reference Notes
Fotheringham, A. S., Brunsdon, C. & Charlton, M. (2002). Geographically Weighted Regression. Wiley. Appendix data descriptions, the origin of the Georgia/London-style example datasets this library's bundled loaders are modelled on

Key papers¶

Paper Contribution
— This chapter is data preparation; see Chapter 6.1's resources for the foundational GWR literature

In this library¶

Object Role
spatialstats.gwmodel.datasets.load_georgia, load_londonhouse, load_beijing_pm25, load_ncovid Synthetic API-demonstration datasets
Chapter 6.3 Where the real diabetes_atlantic data is first modelled
Chapter 6.10 Where the space-time panel subset built here is used