Симметрическая разность (Symmetric Difference) — это геометрическая операция, которая формирует новую область из частей двух объектов, не принадлежащих их пересечению.
Если имеются два полигона A и B, результат симметрической разности включает:
С точки зрения теории множеств операция выглядит следующим образом:
[ A B = (A B) - (A B)]
В геоинформационных системах симметрическая разность применяется для поиска различий между территориями, анализа изменений объектов, сравнения картографических данных и обнаружения расхождений между наборами геометрий.
В библиотеке Turf.js данная операция реализована функцией symmetricDifference().
Современный вариант подключения:
import { symmetricDifference } from "@turf/turf";
Подключение отдельного пакета:
import { symmetricDifference } from "@turf/symmetric-difference";
symmetricDifference(features, options)
| Параметр | Тип | Описание |
|---|---|---|
| features | FeatureCollection<Polygon | MultiPolygon> |
| options | Object | Дополнительные параметры |
Feature<Polygon | MultiPolygon>
или
null
если результат отсутствует.
Пусть существуют два частично пересекающихся прямоугольника.
import * as turf from "@turf/turf";
const polygon1 = turf.polygon([
[
[0, 0],
[6, 0],
[6, 6],
[0, 6],
[0, 0]
]
]);
const polygon2 = turf.polygon([
[
[3, 3],
[9, 3],
[9, 9],
[3, 9],
[3, 3]
]
]);
const collection = turf.featureCollection([
polygon1,
polygon2
]);
const result = turf.symmetricDifference(collection);
console.log(result);
В результате будет создана фигура, состоящая из двух частей:
Центральная пересекающаяся зона будет удалена.
Исходные полигоны:
Polygon A
+-------+
| |
| +-------+
| |###| |
+---|---| |
+-------+
Polygon B
Символами ### обозначено пересечение.
После выполнения симметрической разности:
+-------+
| |
| +---+
| |
+---+ |
+-------+
Общая часть исчезает.
Объединение сохраняет все области.
const result = turf.union(collection);
Результат:
A + B + пересечение
Пересечение сохраняет только общую область.
const result = turf.intersect(collection);
Результат:
только A ∩ B
Разность удаляет второй полигон из первого.
const result = turf.difference(
turf.featureCollection([
polygon1,
polygon2
])
);
Результат:
A - B
Операция является направленной.
Удаляет область пересечения из обоих объектов.
(A ∪ B) - (A ∩ B)
Операция является симметричной:
A △ B = B △ A
Порядок геометрий не влияет на результат.
Функция способна обрабатывать не только два объекта, но и целую коллекцию.
const collection = turf.featureCollection([
polygon1,
polygon2,
polygon3
]);
const result = turf.symmetricDifference(collection);
В этом случае операция выполняется последовательно для всех геометрий.
Например:
(A △ B) △ C
Такой подход позволяет находить области, принадлежащие нечётному количеству перекрывающихся объектов.
Одной из наиболее распространённых задач является сравнение двух версий полигона.
Предположим, имеется граница лесного массива за разные годы.
const forest2023 = turf.polygon(...);
const forest2024 = turf.polygon(...);
const result = turf.symmetricDifference(
turf.featureCollection([
forest2023,
forest2024
])
);
Полученная геометрия показывает:
Такой подход активно применяется при мониторинге:
Функция поддерживает объекты типа MultiPolygon.
Создание мультиполигона:
const multiPolygon = turf.multiPolygon([
[
[
[0, 0],
[3, 0],
[3, 3],
[0, 3],
[0, 0]
]
],
[
[
[5, 5],
[8, 5],
[8, 8],
[5, 8],
[5, 5]
]
]
]);
Использование:
const collection = turf.featureCollection([
polygon1,
multiPolygon
]);
const result = turf.symmetricDifference(collection);
Результатом может стать как Polygon, так и MultiPolygon.
После вычисления симметрической разности часто возникает необходимость узнать площадь изменений.
const diff = turf.symmetricDifference(collection);
const area = turf.area(diff);
console.log(area);
Так можно определить:
Рассмотрим ситуацию, когда имеются два набора границ земельного участка.
const parcelOld = turf.polygon(...);
const parcelNew = turf.polygon(...);
const diff = turf.symmetricDifference(
turf.featureCollection([
parcelOld,
parcelNew
])
);
Если площадь результата равна нулю либо результат отсутствует:
if (!diff) {
console.log("Изменений нет");
}
Тогда геометрии совпадают.
В противном случае симметрическая разность покажет все отличающиеся фрагменты.
Симметрическая разность позволяет определить, являются ли полигоны идентичными.
const diff = turf.symmetricDifference(
turf.featureCollection([
polygonA,
polygonB
])
);
const isEqual = diff === null;
Логика проста:
Такой подход часто используется при автоматической проверке качества пространственных данных.
Перед дальнейшей работой желательно убедиться в наличии результата.
const result = turf.symmetricDifference(collection);
if (result) {
console.log(result.geometry.type);
}
Тип геометрии может быть:
Polygon
или
MultiPolygon
Поэтому код обработки должен учитывать оба варианта.
На практике операция обычно используется совместно с другими инструментами Turf.js.
const diff = turf.symmetricDifference(collection);
if (diff) {
const simplified = turf.simplify(diff, {
tolerance: 0.001
});
const area = turf.area(simplified);
console.log(area);
}
Последовательность действий:
Функция предназначена для работы с:
Использование точек и линий недопустимо.
const point = turf.point([0, 0]);
turf.symmetricDifference(
turf.featureCollection([
point,
polygon
])
);
Такой код приведёт к ошибке.
Полигон должен быть валидным.
Проблемы могут возникать при наличии:
Перед выполнением булевых операций часто применяются инструменты очистки данных.
Симметрическая разность относится к вычислительно сложным операциям.
Особенно затратными являются случаи:
Для повышения производительности используются:
turf.simplify()
и предварительная фильтрация объектов по пространственным индексам.
Сравнение старой и новой версии карты.
const changes = turf.symmetricDifference(
turf.featureCollection([
oldMap,
newMap
])
);
Поиск несовпадений между данными разных поставщиков.
const mismatch = turf.symmetricDifference(
turf.featureCollection([
providerA,
providerB
])
);
Определение новых строительных площадок.
const newBuildings = turf.symmetricDifference(
turf.featureCollection([
city2024,
city2025
])
);
Сравнение контуров:
const environmentalChanges =
turf.symmetricDifference(
turf.featureCollection([
oldBoundary,
newBoundary
])
);
symmetricDifference() представляет собой булеву геометрическую операцию, удаляющую пересекающиеся части объектов и сохраняющую только различающиеся области. Функция работает с Polygon и MultiPolygon, поддерживает обработку коллекций геометрий, возвращает Polygon или MultiPolygon и широко применяется для анализа изменений, контроля качества пространственных данных, сравнения версий карт и поиска расхождений между наборами геометрий.