Геолокация и карты в Rust: обзор библиотек и инструментов

Онлайн-тренажер Python для начинающих

Изучайте Python легко и без перегрузки теорией. Решайте практические задачи с автоматической проверкой, получайте подсказки на русском языке и пишите код прямо в браузере — без необходимости что-либо устанавливать.

Начать курс

Геолокация и карты в Rust: обзор инструментов и примеры кода

Rust — язык системного программирования, который всё чаще используется для создания высоконагруженных сервисов, работающих с пространственными данными. Благодаря производительности, безопасности памяти и активному сообществу, экосистема Rust предлагает несколько зрелых библиотек для работы с геолокацией, картами и форматами геоданных. В этой статье мы рассмотрим ключевые инструменты: geo, georust (включая gpx и geojson), а также интеграцию с картографическими библиотеками через WebAssembly.

1. Основная библиотека: geo

Библиотека geo — это ядро экосистемы геопространственных вычислений в Rust. Она предоставляет типы данных (точки, линии, полигоны), алгоритмы (расчет расстояний, площади, пересечений) и поддержку популярных координатных систем (WGS84, UTM).

Установка

# Cargo.toml
[dependencies]
geo = "0.27"

Пример: расчет расстояния между двумя точками

use geo::{point, Distance};

fn main() {
    let moscow = point!(x: 37.6173, y: 55.7558);
    let london = point!(x: -0.1276, y: 51.5074);

    // Расстояние по сфере (алгоритм Хаверсина)
    let distance = moscow.distance_haversine(&london);
    println!("Расстояние от Москвы до Лондона: {:.2} км", distance / 1000.0);
}

Библиотека поддерживает:

  • Типы геометрий: Point, LineString, Polygon, MultiPoint и др.
  • Алгоритмы: буферизация, упрощение линий (Ramer-Douglas-Peucker), расчет центроида.
  • Работу с CRS через крейт proj.

2. Работа с форматами: GeoJSON и GPX

Для чтения и записи геоданных используются отдельные крейты из экосистемы georust.

GeoJSON

Крейт geojson позволяет сериализовать/десериализовать GeoJSON — стандартный формат обмена геоданными.

use geojson::{Feature, GeoJson, Geometry, Value};
use serde_json;

fn main() {
    let geojson_str = r#"{
        "type": "Feature",
        "geometry": {
            "type": "Point",
            "coordinates": [37.6173, 55.7558]
        },
        "properties": {
            "name": "Moscow"
        }
    }"#;

    let geojson: GeoJson = geojson_str.parse().unwrap();
    if let GeoJson::Feature(feature) = geojson {
        println!("Геометрия: {:?}", feature.geometry);
    }
}

GPX (GPS Exchange Format)

Крейт gpx предназначен для работы с треками и путевыми точками, записанными GPS-устройствами.

use gpx::read;
use std::fs::File;

fn main() {
    let file = File::open("track.gpx").unwrap();
    let gpx = read(file).unwrap();

    for track in gpx.tracks {
        println!("Название трека: {:?}", track.name);
        for segment in track.segments {
            for point in segment.points {
                println!("Точка: ({:.4}, {:.4})", point.point().x(), point.point().y());
            }
        }
    }
}

3. Визуализация карт: Leaflet.js через WASM

Для отображения карт на веб-странице можно использовать Leaflet.js в связке с Rust через WebAssembly. Популярный подход — генерация HTML/JavaScript на стороне Rust с помощью крейта wasm-bindgen и встраивание карты через leaflet.js.

Пример: создание карты с маркером

// cargo.toml
[dependencies]
wasm-bindgen = "0.2"

// main.rs
use wasm_bindgen::prelude::*;

#[wasm_bindgen]
pub fn init_map() {
    let window = web_sys::window().unwrap();
    let document = window.document().unwrap();

    // Создаем div для карты
    let map_div = document.create_element("div").unwrap();
    map_div.set_attribute("id", "map").unwrap();
    map_div.set_attribute("style", "height: 400px;").unwrap();
    document.body().unwrap().append_child(&map_div).unwrap();

    // Встраиваем скрипт Leaflet
    let script = document.create_element("script").unwrap();
    script.set_inner_html(r#"
        var map = L.map('map').setView([55.7558, 37.6173], 10);
        L.tileLayer                    

Рекомендаций