Skip to article frontmatterSkip to article content
Site not loading correctly?

This may be due to an incorrect BASE_URL configuration. See the MyST Documentation for reference.

Чтение векторных данных

В предыдущем разделе мы познакомились с моделями пространственных данных, рассмотрели принципы их описания и создали набор пространственных данных в формате GeoDataFrame на основе координат точки.

Однако в реальных задачах пространственный анализ чаще всего выполняется на основе уже подготовленных и сохранённых наборов данных, которые необходимо корректно загрузить и обработать.

В этом разделе разберём, в каких форматах хранятся пространственные данные и как их загружать в Python.

0. Импорт библиотек

import pandas as pd
import geopandas as gpd
  • pandas (pandas) — библиотека Python для работы с табличными данными.

  • GeoPandas (geopandas) — библиотека Python, расширение библиотеки pandas, предназначенное для работы с геопространственными данными. Позволяет загружать, обрабатывать и анализировать пространственные наборы данных в различных форматах.

1. Форматы векторных данных

Для хранения пространственных векторных данных есть специальные файловые форматы. Рассмотрим наиболее распространённые из них:

  1. Shapefile (.shp)

    Формат, разработанный компанией Esri и широко используемый в геоинформационных системах. Представляет собой набор взаимосвязанных файлов (.shp — геометрия, .shx — индекс, .dbf — атрибуты), которые совместно создают единый набор данных.

  2. GeoJSON (.geojson)

    Текстовый формат на основе JSON, широко используемый в веб-картографии. Удобен для обмена данными и хорошо читается, но не очень эффективен для больших объёмов данных.

  3. GeoPackage (.gpkg)

    Современный формат хранения пространственных данных, основанный на SQLite. Открытый стандарт, разработанный Open Geospatial Consortium. По сути представляет собой базу данных.

Для загрузки пространственных данных используется функция read_file() библиотеки GeoPandas.

В примерах будут использованы файлы из нашего репозитория:

  • spb_dtp.shp — точечные данные о ДТП в Санкт-Петербурге за январь 2023 года.
    Источник: Карта ДТП

  • spb_metro.geojson — точечные данные о станциях метро в Санкт-Петербурге (2023).
    Источник: Портал открытых данных Санкт-Петербурга

  • spb_admin.gpkg — полигональные данные о границах районов и округов Санкт-Петербурга.
    Источник: материалы курса «Методы пространственного анализа», НИУ ВШЭ (Р. Гончаров)

  • spb_theaters.csv — данные о театрах Санкт-Петербурга.
    Источник: Портал открытых данных Санкт-Петербурга

Ниже рассмотрим пример импорта данных различных форматов.

Вы можете применять те же команды для работы с собственными данными аналогичных форматов.

1.1. Shapefile

При работе с этим форматом важно учитывать, что он представляет собой не один файл, а набор взаимосвязанных файлов. Для корректного чтения данных минимально необходимы:

  • .shp — геометрия

  • .dbf — атрибуты

  • .shx — индекс

  • .prj — система координат

Несмотря на то что при загрузке мы указываем путь только к файлу .shp, все остальные файлы должны находиться в той же директории.

gdf_shp = gpd.read_file("data/spb_dtp_shp/spb_dtp.shp")

Выведем первые пять строк атрибутивной таблицы с помощью метода head():

gdf_shp.head()
Loading...

Посмотрим на данные на карте с помощью метода explore():

Параметр tiles отвечает за выбор фоновой карты. В примере используется светлая подложка cartodbpositron. Если этот параметр не указывать, по умолчанию будет использована стандартная подложка OpenStreetMap.

gdf_shp.explore(tiles='cartodbpositron')
Loading...

1.2. GeoJSON

В отличие от Shapefile, формат GeoJSON представляет собой единый файл, в котором в текстовом формате одновременно хранятся геометрия объектов, их атрибуты и информация о системе координат.

gdf_geojson = gpd.read_file("data/spb_metro.geojson") 

Выведем первые пять строк атрибутивной таблицы с помощью метода head():

gdf_geojson.head()
Loading...

Посмотрим на данные на карте с помощью метода explore():

gdf_geojson.explore(tiles='cartodbpositron')
Loading...

1.3. GeoPackage

При работе с форматом .gpkg важно учитывать, что внутри одного файла может храниться несколько наборов данных (слоёв). В этом случае при чтении необходимо явно указать, какой именно слой требуется загрузить; иначе по умолчанию будет прочитан первый доступный слой.

Чтобы определить, какие слои содержатся в файле .gpkg, можно воспользоваться методом list_layers().

gpd.list_layers("data/spb_admin.gpkg")
Loading...

Эта команда вернула список доступных слоёв, один из которых можно указать при чтении файла с помощью параметра layer.

gdf_gpkg = gpd.read_file("data/spb_admin.gpkg", layer="okrug")

Выведем первые пять строк атрибутивной таблицы с помощью метода head():

gdf_gpkg.head()
Loading...

Посмотрим на данные на карте с помощью метода explore():

gdf_gpkg.explore(tiles='cartodbpositron')
Loading...

2. Табличные данные

Иногда пространственная информация хранится только в виде координат и не содержит явной геометрии. Например, в табличных данных для объектов могут быть указаны долгота и широта. В таком виде данные сами по себе не являются пространственными. Однако на основе координат можно сформировать геометрию объектов и создать набор пространственных данных в формате GeoDataFrame.

Один из наиболее распространённых форматов хранения табличных данных — CSV (Comma-Separated Values). Это простой текстовый формат, в котором значения в строках разделяются специальным символом (чаще всего запятой).

Рассмотрим, как на основе табличных данных с координатами создать полноценный набор пространственных данных.

2.1. Чтение CSV

Загрузим CSV-файл с помощью функции read_csv() библиотеки pandas:

df_csv = pd.read_csv('./data/spb_theaters.csv')

Выведем первые десять строк атрибутивной таблицы с помощью метода head(), чтобы познакомиться со структурой данных и определить, в каких полях содержатся координаты:

df_csv.head()
Loading...

Значения координат в таблице содержатся в полях latitude (широта - Y) и longitude (долгота - X).

Запишем названия в отдельные переменные:

X = "longitude"
Y = "latitude"

2.2. Создание GeoDataFrame

Преобразуем координаты из полей с координатами в геометрию точек с помощью функции points_from_xy() библиотеки GeoPandas:

#удалим строки с пустыми координатами
df_csv = df_csv.dropna(subset=[X, Y]) 

#создадим геометрию
geometry = gpd.points_from_xy(df_csv[X], df_csv[Y])

#посмотрим на первые пять объектов
geometry[:5]
<GeometryArray> [<POINT (30.335 59.936)>, <POINT (30.345 59.93)>, <POINT (30.343 59.943)>, <POINT (30.338 59.934)>, <POINT (30.336 59.932)>] Length: 5, dtype: geometry

Создадим GeoDataFrame, добавив сформированную геометрию к исходной таблице:

gdf_csv = gpd.GeoDataFrame(df_csv, geometry=geometry, crs="EPSG:4326")

Здесь мы:

  • передаём исходную таблицу df_csv,

  • добавляем геометрию,

  • указываем систему координат (EPSG:4326 — географическая система координат WGS-84).

Выведем первые пять строк атрибутивной таблицы с помощью метода head():

gdf_csv.head()
Loading...

Посмотрим на данные на карте с помощью метода explore():

gdf_csv.explore(tiles='cartodbpositron')
Loading...

2.3. Сохранение результата

После создания GeoDataFrame полученный набор пространственных данных можно сохранить в любом поддерживаемом формате. Для этого используется метод to_file() библиотеки GeoPandas.

# сохранение в формате Shapefile
# gdf_csv.to_file("gdf_csv.shp")

# сохранение в формате GeoJSON
# gdf_csv.to_file("gdf_csv.geojson", driver="GeoJSON")

# сохранение в формате GeoPackage
# gdf_csv.to_file("gdf_csv.gpkg", layer="data", driver="GPKG")

Формат файла определяется расширением и/или параметром driver (опционален). Для .gpkg рекомендуется указывать имя слоя через параметр layer.

3. Итог

В этом разделе мы познакомились с основными форматами хранения векторных пространственных данных и научились импортировать их в Python с помощью библиотеки GeoPandas.

Мы рассмотрели особенности форматов Shapefile, GeoJSON и GeoPackage, а также разобрали различия в их структуре и способах чтения.

Кроме того, мы изучили, как работать с табличными данными в формате CSV, создавать геометрию на основе координат и формировать объект типа GeoDataFrame.