Выражения для match

Синтаксис и базовая структура

Выражение match представляет собой дискретное сопоставление значений, аналогичное конструкции switch-case в императивных языках, но встроенное в декларативную систему стилей MapLibre GL JS.

Формальная структура:

["match", input, matchValue1, output1, matchValue2, output2, ..., fallback]
  • input — выражение, значение которого вычисляется для каждого объекта (например, свойство feature)
  • matchValueN — значение, с которым выполняется сравнение
  • outputN — результат, возвращаемый при совпадении
  • fallback — значение по умолчанию, если совпадений не найдено

Ключевая особенность заключается в том, что сопоставление выполняется строго и без неявных преобразований типов.


Механика вычисления

При обработке выражения match происходит последовательная проверка:

  1. Вычисляется input
  2. Значение сравнивается с каждым matchValue по порядку
  3. При первом совпадении возвращается соответствующий output
  4. Если совпадений нет, используется fallback

Принцип работы можно представить как линейный поиск по таблице соответствий.


Строгость сравнения и типы данных

Сравнение в match не допускает приведения типов. Это означает:

  • строка "1" не равна числу 1
  • true не равен "true"
  • массивы сравниваются по структуре и содержимому

Примеры:

["match", ["get", "type"],
  "road", "#ff0000",
  "water", "#0000ff",
  "#cccccc"
]

Если feature.properties.type = "road", результатом будет #ff0000.

При этом:

["match", ["get", "id"],
  1, "red",
  "1", "blue",
  "gray"
]

значение 1 и "1" рассматриваются как разные случаи.


Использование свойств feature

Наиболее частый сценарий применения — стилизация объектов по атрибутам GeoJSON или векторных тайлов.

"fill-color": [
  "match",
  ["get", "class"],
  "park", "#2ecc71",
  "water", "#3498db",
  "industrial", "#95a5a6",
  "#e0e0e0"
]

Здесь значение свойства class определяет цвет заливки.

Такая схема позволяет:

  • централизованно описывать стили
  • избегать множества слоёв
  • снижать сложность конфигурации карты

Работа с несколькими значениями

match поддерживает сопоставление с несколькими возможными значениями для одного результата через вложенные массивы.

["match", ["get", "type"],
  ["road", "highway"], "#ff9900",
  ["river", "stream"], "#3399ff",
  "#999999"
]

Если значение type равно "road" или "highway", будет выбран один и тот же результат.

Такой подход позволяет:

  • группировать категории
  • уменьшать дублирование выражений
  • упрощать поддержку стилей

Типы возвращаемых значений

match может возвращать любые допустимые типы значений MapLibre GL JS:

  • цвета (string)
  • числа (например, ширина линии)
  • массивы (RGBA, offset, blur)
  • булевы значения
  • другие выражения

Пример изменения толщины линии:

"line-width": [
  "match",
  ["get", "highway"],
  "primary", 4,
  "secondary", 2,
  "tertiary", 1,
  0.5
]

Использование в paint и layout свойствах

match применяется как в визуальных свойствах (paint), так и в свойствах макета (layout).

Пример управления видимостью слоя:

"layout": {
  "visibility": [
    "match",
    ["get", "show"],
    true, "visible",
    "none"
  ]
}

Пример динамического текста:

"text-size": [
  "match",
  ["get", "rank"],
  "major", 16,
  "minor", 12,
  10
]

Вложенные выражения

match часто используется внутри других выражений, включая case, let, coalesce, арифметические операции.

["case",
  ["==", ["get", "type"], "road"],
  ["match", ["get", "class"],
    "primary", "#ff0000",
    "secondary", "#ff8800",
    "#cccccc"
  ],
  "#000000"
]

Такой подход позволяет строить многоуровневую логику стилизации.


Работа с отсутствующими значениями

Если входное значение отсутствует (null или undefined), match не выполняет совпадений и сразу возвращает fallback.

["match", ["get", "category"],
  "a", 1,
  "b", 2,
  0
]

Если category отсутствует, результатом будет 0.


Особенности поведения с числами

Числовые значения сравниваются строго, включая тип float/integer.

["match", ["get", "level"],
  1, "#00ff00",
  2, "#ffff00",
  3, "#ff0000",
  "#999999"
]

Если level = 1.0, совпадение происходит, так как значение интерпретируется как число 1, но любые отклонения типа или структуры приводят к промаху.


Производительность и оптимизация

match является линейным по сложности: O(n), где n — количество пар значений.

При больших наборах данных это важно учитывать:

  • длинные цепочки match замедляют рендеринг
  • предпочтительно группировать значения
  • для диапазонов лучше использовать step или interpolate

Сравнение:

  • match — дискретные категории
  • step — числовые диапазоны
  • interpolate — плавные переходы

Использование с цветами и визуальными шкалами

Наиболее распространённый сценарий — категоризация объектов:

"circle-color": [
  "match",
  ["get", "mag_type"],
  "md", "#2ecc71",
  "ml", "#f1c40f",
  "ms", "#e67e22",
  "#95a5a6"
]

Здесь каждый тип события получает уникальный цвет, а неизвестные значения окрашиваются в нейтральный оттенок.


Сопоставление с логическими значениями

Булевы значения также допустимы:

"visibility": [
  "match",
  ["get", "active"],
  true, "visible",
  false, "none",
  "none"
]

При этом важно учитывать, что строковое "true" не эквивалентно булевому true.


Взаимодействие с другими выражениями

match часто комбинируется с:

  • get — извлечение свойств
  • to-string, to-number — приведение типов
  • coalesce — обработка null
  • case — условные цепочки

Пример с нормализацией:

["match",
  ["to-string", ["get", "type"]],
  "road", "#ff0000",
  "water", "#0000ff",
  "#cccccc"
]

Типичные ошибки использования

На практике часто возникают ошибки:

  • отсутствие fallback-значения
  • несоответствие типов
  • попытка использовать диапазоны вместо категорий
  • чрезмерно длинные списки значений

Отсутствие fallback приводит к возвращению undefined, что может вызвать некорректную отрисовку слоя.


Сравнение с альтернативами

Выражение Назначение Поведение
match Категории точное сопоставление
step Пороговые значения интервалы
interpolate Плавные переходы непрерывные шкалы

match занимает центральное место в задачах категоризации данных в визуализации карт.


Использование в реальных слоях карты

Комбинированный пример слоя линий:

{
  "id": "roads",
  "type": "line",
  "source": "vector",
  "source-layer": "transportation",
  "paint": {
    "line-color": [
      "match",
      ["get", "road_class"],
      "motorway", "#d73027",
      "trunk", "#fc8d59",
      "primary", "#fee08b",
      "#cccccc"
    ],
    "line-width": [
      "match",
      ["get", "road_class"],
      "motorway", 3,
      "trunk", 2.5,
      "primary", 2,
      1
    ]
  }
}

Такой подход позволяет одной конфигурацией охватывать весь класс дорог без создания отдельных слоёв.


Поведение при больших наборах категорий

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

  • нормализация данных на стороне источника
  • генерация стилей
  • использование lookup-таблиц в приложении

Тем не менее, match остаётся стандартным инструментом декларативной стилизации.


Композиция с вычисляемыми значениями

match может работать с результатами арифметических или логических выражений:

["match",
  ["+", ["get", "a"], ["get", "b"]],
  0, "none",
  1, "low",
  2, "medium",
  "high"
]

Такое использование позволяет строить производные категории без изменения исходных данных.