Exports para Observable / D3
Cuaderno suplementario del CRC002. Genera los archivos planos
(JSON, GeoJSON) en observable/data/ que alimentan la galería interactiva del proyecto Riesgos.
Prerrequisito: ejecutar
article.ipynben la misma sesión de kernel (o descomentar la celda%runa continuación) para disponer de las variablesdf_idx,OUT_OBS,SSP_LABELS,delta_field,lst_mean,lst_p90,df_zonaly los parámetros de grilla.
# Descomentar si se ejecuta este cuaderno de forma independiente
# %run ../article.ipynb1. Exports Fase 1 — Hazard climatológico¶
Tres archivos planos que el sitio MyST de la scr-ungrd puede consumir sin re-correr el
pipeline. Alimentan la galería interactiva del proyecto Riesgos.
# 5.1 Serie temporal plana
ts_export = df_idx.copy()
ts_export['scenario_label'] = ts_export['scenario'].map(SSP_LABELS)
ts_export[['scenario', 'scenario_label', 'year', 'member',
'HWF', 'HWML', 'TR_nights', 'TX35']] .to_json(OUT_OBS / 'hazard_timeseries.json', orient='records')
# 5.2 Estadísticas del ensamble (banda + línea)
df_stats_export = df_stats.copy()
df_stats_export['scenario_label'] = df_stats_export['scenario'].map(SSP_LABELS)
df_stats_export.to_json(OUT_OBS / 'hazard_ensemble_stats.json', orient='records')
# 5.3 GeoJSON del cambio espacial
features = []
for i in range(ny):
for j in range(nx):
poly = [
[float(lons[j]-dlon), float(lats[i]-dlat)],
[float(lons[j]+dlon), float(lats[i]-dlat)],
[float(lons[j]+dlon), float(lats[i]+dlat)],
[float(lons[j]-dlon), float(lats[i]+dlat)],
[float(lons[j]-dlon), float(lats[i]-dlat)],
]
features.append({
'type': 'Feature',
'geometry': {'type': 'Polygon', 'coordinates': [poly]},
'properties': {'delta_hwf': round(float(delta_field[i, j]), 2)},
})
geojson = {
'type': 'FeatureCollection',
'name': 'Δ HWF SSP5-8.5 (2021-2050) vs referencia',
'metadata': {
'units': 'events/year',
'source': 'Pattern scaling sobre GMST CMIP6, ensamble sintético',
'value_field': 'delta_hwf',
},
'features': features,
}
with open(OUT_OBS / 'hazard_delta_hwf.geojson', 'w', encoding='utf-8') as f:
json.dump(geojson, f, ensure_ascii=False, separators=(',', ':'))
for fname in ('hazard_timeseries.json',
'hazard_ensemble_stats.json',
'hazard_delta_hwf.geojson'):
size = (OUT_OBS / fname).stat().st_size
print(f" ✓ {fname:<35s} ({size//1024} KB)")
✓ hazard_timeseries.json (557 KB)
✓ hazard_ensemble_stats.json (32 KB)
✓ hazard_delta_hwf.geojson (35 KB)
2. Exports Fase 2 — Urban Heat Island¶
Tres archivos planos consumibles desde el sitio MyST o desde dashboards externos.
# 6.7.1 GeoJSON del raster LST media
features_lst = []
for i in range(ny_lst):
for j in range(nx_lst):
poly = [
[float(lons_lst[j]-dlon_lst), float(lats_lst[i]-dlat_lst)],
[float(lons_lst[j]+dlon_lst), float(lats_lst[i]-dlat_lst)],
[float(lons_lst[j]+dlon_lst), float(lats_lst[i]+dlat_lst)],
[float(lons_lst[j]-dlon_lst), float(lats_lst[i]+dlat_lst)],
[float(lons_lst[j]-dlon_lst), float(lats_lst[i]-dlat_lst)],
]
features_lst.append({
'type': 'Feature',
'geometry': {'type': 'Polygon', 'coordinates': [poly]},
'properties': {
'lst_mean': round(float(lst_mean[i, j]), 2),
'lst_p90': round(float(lst_p90[i, j]), 2),
},
})
geo_lst = {
'type': 'FeatureCollection',
'name': 'LST media + P90 Cartagena (Modo A sintético)',
'metadata': {
'units': '°C',
'source': 'Synthetic LST calibrated to Caribbean coastal UHI literature',
'value_fields': ['lst_mean', 'lst_p90'],
},
'features': features_lst,
}
with open(OUT_OBS / 'uhi_lst_raster.geojson', 'w', encoding='utf-8') as f:
json.dump(geo_lst, f, ensure_ascii=False, separators=(',', ':'))
# 6.7.2 JSON plano del resumen zonal
df_zonal.to_json(OUT_OBS / 'uhi_zonal_summary.json', orient='records')
for fname in ('uhi_lst_raster.geojson', 'uhi_zonal_summary.json'):
size = (OUT_OBS / fname).stat().st_size
print(f" ✓ {fname:<35s} ({size//1024} KB)")
✓ uhi_lst_raster.geojson (1096 KB)
✓ uhi_zonal_summary.json (0 KB)