Geovisualización¶

Manejando objetos geográficos con GeoPandas¶

Nota: Para instalar las dependencias en Colab, copien las siguientes líneas en una celda y ejecútenla.

# Important library for many geopython libraries
!apt install gdal-bin python-gdal python3-gdal 
# Install rtree - Geopandas requirment
!apt install python3-rtree 
# Install Geopandas
!pip install git+git://github.com/geopandas/geopandas.git
# Install descartes - Geopandas requirment
!pip install descartes 
# Install Folium for Geographic data visualization
!pip install folium
# Install plotlyExpress
!pip install mapclassify
!pip install palettable
In [1]:
import matplotlib.pyplot as plt
import geopandas as gpd
import palettable as pltt
from seaborn import palplot
import requests

En esta práctica, aprenderemos a importar, manipular y visualizar datos espaciales. Hasta cierto punto, los datos espaciales han sido tan propagados que existen casos en los que únicamente se consideran como "una columna más" dentro de una tabla; sin embargo, existen múltiples características que distinguen enormemente a los datos geográficos de las tablas numéricas comúnes.

En esta sesión, vamos a construir a partir de las habilidades desarolladas en la práctica de Transformación de Datos, para combinarlas y, en el proceso, descubrir que, salvo algunas particularidades, tratar con datos espaciales en Python se asemeja mucho al manejo de datos no espaciales.

Para esto, se utilizarán los datos derivados del Censo de Población y Vivienda 2010 de INEGI, así como la geografía utilizada para su construcción, lo cual puede ser consultado a través de este link, y descargado por este otro.

En primer lugar, como se hizo en la primera práctica, y por cuestiones de conveniencia, se definirá una variable de tipo string donde se almacene la ubicación de los datos de trabajo:

In [2]:
# Recuerda que podría ser diferente en tu caso, dependiendo de en dónde almacenes los datos
f = 'data/'

Nota para Google Colab: Para trabajar este taller en Colab, podemos bajar los datos de la siguiente forma:

url = "https://www.dropbox.com/s/fkyz9a36dlxgaoa/agebs_cdmx.geojson?dl=1"
r = requests.get(url, allow_redirects=True)
open('/content/agebs_cdmx.geojson', 'wb').write(r.content)
url = "https://www.dropbox.com/s/fs1n5um80n2gtme/vias_cuauhtemoc.geojson?dl=1"
r = requests.get(url, allow_redirects=True)
open('/content/vias_cuauhtemoc.geojson', 'wb').write(r.content)
url = "https://www.dropbox.com/s/h82435z8lcn97g3/estaciones_metro.zip?dl=1"
r = requests.get(url, allow_redirects=True)
open('/content/estaciones_metro.zip', 'wb').write(r.content)
url = "https://www.dropbox.com/s/rfx4t2989y834lm/poblacion_cdmx.csv?dl=1"
r = requests.get(url, allow_redirects=True)
open('/content/poblacion_cdmx.csv', 'wb').write(r.content)
# Carpeta de datos
f = "/content/"

Importando Datos Espaciales¶

La forma más fácil y rápida de importar datos espaciales es a través de un objeto del tipo GeoDataFrame, que tiene la capacidad de interpretar cuáles son las columnas donde se almacena la componente espacial, ausente en un DataFrame convencional; además, se puede visualizar rápidamente a través del comando .plot().

La librería principal utilizada para el manejo de datos espaciales recibe el nombre de geopandas, la cual es una extensión geoespacial de la librería pandas con la que se ha trabajado hasta ahora. geopandas ofrece exactamente la misma funcionalidad de pandas, debido a que la primera fue construída a partir de la segunda, añadiendo un conjunto de funciones de caracter espacial que permiten que la manipulación y transformación de los datos espaciales sea tan sencilla como con los datos no espaciales.

En sólo dos líneas de código es posible obtener una representación gráfica de los datos espaciales contenidos en un archivo, siendo posible manejar una gran variedad de formatos; de hecho, debido a que ambos manejan el mismo tipo de drivers, la gran mayoría de los archivos vectoriales que son aceptados en QGIS pueden ser aceptados por geopandas. Comenzaremos por graficar una capa a la vez de forma tosca pero veloz, para poco a poco agregar estilo y sofisticación.

Polígonos¶

Comenzando por uno de los tipos de datos espaciales más comunes, Polígonos, se importará la geografía de todas las AGEB's que conforman la Ciudad de México, a través de la funcion .read_file() de geopandas; asimismo, se utilizará el método .set_index() para determinar su Clave Geográfica (CVEGEO) como el índice de cada fila:

In [3]:
agebs = gpd.read_file(f + 'agebs_cdmx.geojson')  # Importar los datos espaciales
agebs = agebs.set_index('ageb_urbana_cvegeo')    # Seleccionar su Clave Geográfica como el índice de las filas

La variable agebs contiene un objeto del tipo GeoDataFrame, el cual es muy similar a los DataFrame manejados en la práctica anterior, pero con una nueva columna llamada geometry:

In [4]:
agebs.head()
Out[4]:
geometry
ageb_urbana_cvegeo
0900700013628 MULTIPOLYGON (((-99.03887 19.39128, -99.03851 ...
0900300011533 MULTIPOLYGON (((-99.18010 19.30772, -99.17845 ...
0901500010235 MULTIPOLYGON (((-99.14495 19.45625, -99.14536 ...
0900200010097 MULTIPOLYGON (((-99.20573 19.50454, -99.20630 ...
0900200011184 MULTIPOLYGON (((-99.20723 19.50387, -99.20652 ...

Como tal, es posible graficar rápidamente este GeoDataFrame a través de la instrucción .plot():

In [5]:
agebs.plot(figsize = (10,10))
Out[5]:
<AxesSubplot:>

Aunque no se trata de la visualización estética de las AGEB's, si permite visualizar rápidamente la apariencia de éstas; más adelante se aprenderá cómo mejorar la apariencia visual y personalizar estas representaciones.

¡Importante Si se utiliza la función .loc() aprendida en la práctica anterior para llamar una sola fila y su columna geometry, de forma automática se obtendrá una pequeña gráfica del shape en cuestión; debido a que el índice es la Clave Geográfica, éste puede ser utilizado para encontrar el AGEB deseado:

In [6]:
agebs.loc['0901200010337', 'geometry']
Out[6]:

Líneas¶

Visualizar líneas es tan sencillo y directo como lo es con los polígonos. En este caso, se importarán todas las vialidades de la Alcaldía Cuauhtémoc:

In [7]:
vias = gpd.read_file(f + 'vias_cuauhtemoc.geojson') # Se importan los datos espaciales
vias = vias.set_index('id')                         # Se establece una columna como índice
vias.head()                                         # Visualizar los primeros registros de la fila
Out[7]:
geometry
id
1 LINESTRING (-99.17041 19.40092, -99.17047 19.4...
2 LINESTRING (-99.17850 19.40720, -99.17868 19.4...
3 LINESTRING (-99.14905 19.43796, -99.14871 19.4...
4 LINESTRING (-99.14735 19.44531, -99.14718 19.4...
5 LINESTRING (-99.17655 19.42105, -99.17645 19.4...

Al igual que con los polígonos, es posible utilizar la función .plot() para graficar las líneas rápidamente:

In [8]:
vias.plot(figsize = (10,10))
Out[8]:
<AxesSubplot:>