На практике мы редко создаём пространственные данные «с нуля», вручную задавая координаты. Гораздо чаще мы работаем с готовыми наборами данных, которые уже собраны, структурированы и сохранены в различных форматах.
В этом разделе мы научимся загружать пространственные данные из разных источников с помощью Python. В частности, мы рассмотрим:
загрузку векторных форматов (Shapefile, GeoJSON, GeoPackage) с использованием
GeoPandas;работу с CSV-файлами, содержащими координаты;
анализ структуры пространственных данных — их атрибутов и геометрии.
Умение читать и изучать пространственные данные — необходимый шаг перед построением карт, выполнением пространственного анализа или преобразованием данных.
0. Импорт библиотек¶
import pandas as pd
import geopandas as gpdpandas (
pandas) — мощная библиотека Python для анализа и обработки данных. Предоставляет удобные структуры данных, такие как DataFrame, которые идеально подходят для работы с табличными (непространственными) данными — например, CSV-файлами, электронными таблицами или данными из баз данных.GeoPandas (
geopandas) — расширение библиотеки pandas, предназначенное для работы с геопространственными данными. Позволяет загружать, обрабатывать и анализировать пространственные наборы данных в различных форматах.
Работа с различными пространственными форматами¶
Пространственные данные могут храниться в различных форматах файлов — каждый из них предназначен для определённых задач, инструментов и типов анализа.
В этом разделе мы подробнее рассмотрим три наиболее распространённых формата для хранения векторных пространственных данных:
Shapefile (SHP) — классический формат, разработанный компанией Esri; хранит геометрию и атрибуты в нескольких связанных файлах (.shp, .shx, .dbf и др.).
GeoJSON — лёгкий и человекочитаемый формат, основанный на JSON; широко используется в веб-картографии и для обмена пространственными данными.
GeoPackage (GPKG) — современный формат на основе SQLite, сохраняющий данные в одном файле; поддерживает несколько слоёв (векторных, растровых и других).
GeoJSON (or Shapefile)¶
Мы можем загружать пространственные данные напрямую с помощью функции read_file() из библиотеки GeoPandas.
В этом примере мы загружаем файл GeoJSON, содержащий данные о станциях метро в Вене.
После загрузки данных их можно отобразить на интерактивной карте с помощью метода .explore():
metro = gpd.read_file('../data/vienna_metro.geojson')
metro.explore(tiles='cartodbpositron')GeoPackage¶
Мы также можем загружать данные, сохранённые в формате GeoPackage (GPKG), используя ту же функцию read_file() из библиотеки GeoPandas.
В этом примере мы загружаем данные об административных границах Вены:
admin = gpd.read_file('../data/vienna_admin.gpkg')
admin.explore(tiles='cartodbpositron')Готово! Но есть важный момент: файлы GeoPackage могут содержать несколько слоёв.
При необходимости можно указать нужный слой с помощью параметра layer=.
Если этого не сделать, по умолчанию будет загружен только первый слой из файла.
Чтобы узнать, какие слои содержатся в файле GeoPackage, можно воспользоваться функцией listlayers из библиотеки fiona.
Давайте импортируем библиотеку и посмотрим, какие слои доступны.
import fiona
layers = fiona.listlayers('../data/vienna_admin.gpkg')
print(layers)['districts']
Теперь мы знаем, какие слои содержатся в нашем файле GeoPackage, и можем обращаться к ним по имени.
admin_district = gpd.read_file('../data/vienna_admin.gpkg', layer="cadastral_districts")
admin_district.explore(tiles='cartodbpositron')Отлично! Мы научились загружать пространственные данные из наиболее распространённых форматов — включая GeoJSON, Shapefile и GeoPackage.
Теперь, когда мы уверенно можем читать пространственные наборы данных, можно переходить к работе с ними и их анализу.
Создание пространственных данных из табличных данных¶
Иногда мы начинаем не с пространственного файла, а с табличных данных (например, CSV-файла), в которых для каждого объекта указаны координаты.
В этом разделе мы научимся загружать такие табличные данные и преобразовывать их в GeoDataFrame для последующего пространственного анализа.
CSV¶
CSV (Comma-Separated Values) — это текстовый формат, широко используемый для хранения табличных данных. По своей природе он не является пространственным форматом, однако часто применяется в геоаналитике, если файл содержит поля с координатами, например долготу и широту.
В таких случаях мы можем извлечь координаты и использовать их для создания пространственных объектов (например, точек).
Давайте загрузим CSV-файл с помощью библиотеки pandas и посмотрим на его структуру. Это поможет понять, как организованы данные и где именно хранятся координаты.
poi = pd.read_csv('../data/top_locations_wien.csv', sep=";", decimal=',')
poi.head()Перед нами список «топ-локаций» в Вене. Координаты объектов хранятся в столбцах geo_latitude и geo_longitude.
Чтобы работать с этим набором как с пространственными данными, нам нужно преобразовать его в GeoDataFrame.
Чтобы преобразовать обычный DataFrame в GeoDataFrame, нужно:
Создать геометрию (в нашем случае — точки) на основе столбцов с координатами. Для этого удобно использовать функцию
points_from_xy()из GeoPandas: она принимает значения долготы и широты и возвращает список геометрийPoint.Записать полученные геометрии в новый столбец
geometry.Задать систему координат (CRS) — здесь мы используем EPSG:4326, то есть стандартную систему широта/долгота WGS84, которая используется в GPS.
poi_gdf = gpd.GeoDataFrame(poi, geometry=gpd.points_from_xy(poi['geo_longitude'], poi['geo_latitude']), crs=4326)Давайте посмотрим на результат.
poi_gdf.explore(tiles='cartodbpositron')Готово — мы успешно преобразовали наши табличные данные в пространственный набор данных!
Исследование данных¶
После загрузки пространственного набора данных в GeoDataFrame важно разобраться, что именно он содержит.
Вот несколько ключевых характеристик, которые стоит проверить, чтобы лучше понять структуру и особенности данных.
Рассмотрим это на примере набора данных metro (загруженного из файла spb_metro.geojson).
Основная информация¶
metro.info()<class 'geopandas.geodataframe.GeoDataFrame'>
RangeIndex: 98 entries, 0 to 97
Data columns (total 8 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 OBJECTID 98 non-null float64
1 LINFO 98 non-null float64
2 HSTNR 0 non-null float64
3 HTXT 98 non-null object
4 HBEM 5 non-null object
5 EROEFFNUNG 98 non-null float64
6 EROEFFNUN0 98 non-null float64
7 geometry 98 non-null geometry
dtypes: float64(5), geometry(1), object(2)
memory usage: 6.2+ KB
Отображает краткую сводную информацию о DataFrame: количество записей, названия столбцов, типы данных и наличие пропущенных значений.
Просмотр первых строк¶
metro.head()Отображает первые 5 строк набора данных — быстрый способ понять его структуру и содержание
Количество объектов¶
len(metro)
# or
metro.shape(98, 8)Возвращает количество строк (объектов) в наборе данных. Метод .shape также показывает число столбцов.
Тип геомтерии¶
metro.geom_type.unique()array(['Point'], dtype=object)Возвращает количество строк (объектов) в наборе данных. Метод .shape также показывает число столбцов.
Система координат (CRS)¶
metro.crs<Geographic 2D CRS: EPSG:4326>
Name: WGS 84
Axis Info [ellipsoidal]:
- Lat[north]: Geodetic latitude (degree)
- Lon[east]: Geodetic longitude (degree)
Area of Use:
- name: World.
- bounds: (-180.0, -90.0, 180.0, 90.0)
Datum: World Geodetic System 1984 ensemble
- Ellipsoid: WGS 84
- Prime Meridian: GreenwichОтображает систему координат данных — например, EPSG:4326 (WGS84).
Границы набора данных (Bounding Box)¶
metro.total_boundsarray([16.26083539, 48.13051529, 16.50843802, 48.27751795])Возвращает пространственный охват набора данных в виде массива координат: [minx, miny, maxx, maxy].
Поле геометрии¶
metro.geometry0 POINT (16.32423 48.16072)
1 POINT (16.37913 48.20682)
2 POINT (16.42070 48.16965)
3 POINT (16.32776 48.18365)
4 POINT (16.36401 48.22777)
...
93 POINT (16.41480 48.17472)
94 POINT (16.38129 48.21913)
95 POINT (16.26084 48.19696)
96 POINT (16.34295 48.18848)
97 POINT (16.31896 48.18605)
Name: geometry, Length: 98, dtype: geometryОтображает геометрические объекты для каждой строки — именно они представляют пространственную составляющую данных.
Атрибутивные поля¶
metro.columnsIndex(['OBJECTID', 'LINFO', 'HSTNR', 'HTXT', 'HBEM', 'EROEFFNUNG',
'EROEFFNUN0', 'geometry'],
dtype='object')Отображает список всех столбцов в GeoDataFrame, включая столбец geometry и все дополнительные атрибуты.
Обзор¶
print("CRS:", metro.crs)
print("Number of features:", len(metro))
print("Geometry types:", metro.geom_type.unique())
print("Bounds:", metro.total_bounds)
metro.head()CRS: EPSG:4326
Number of features: 98
Geometry types: ['Point']
Bounds: [16.26083539 48.13051529 16.50843802 48.27751795]
Это позволяет быстро получить общее представление о содержании и структуре пространственных данных — важный шаг перед анализом или визуализацией.
Итог¶
В этом модуле мы научились загружать пространственные данные из различных источников и форматов с помощью Python.
В частности, мы рассмотрели:
как загружать векторные форматы данных — Shapefile (SHP), GeoJSON и GeoPackage (GPKG) — с использованием
GeoPandas;как работать с CSV-файлами, содержащими поля широты и долготы, и преобразовывать их в корректный
GeoDataFrameс помощью функцииpoints_from_xy();как анализировать структуру и содержание пространственных данных, включая типы геометрии и атрибуты.
Теперь вы уверенно можете загружать и проверять пространственные данные в разных форматах, подготавливая их к картографированию и дальнейшему геопространственному анализу.