Данные и управление

Конвейеры и заполнители

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

Конвейер показывает, как результат одного шага поступает в следующий. left |> right вычисляет левую часть один раз, сохраняет значение и передаёт его вправо по одному точно определённому правилу. Заполнитель _ отмечает конкретную позицию аргумента вызова, куда попадёт сохранённое значение.

Самодостаточный конвейер

Сохраните код в pipelines-placeholders.tpz:

TOPAZ
function add(value: int, amount: int) -> int {
    value + amount
}

function multiply(left: int, right: int) -> int {
    left * right
}

function equal(left: int, right: int) -> bool {
    left == right
}

let result = 5
    |> add(2)
    |> multiply(_, 3)
let repeated = result |> equal(_, _)

print("{result} {repeated}")

Проверьте и запустите файл:

BASH
topaz check pipelines-placeholders.tpz
topaz run pipelines-placeholders.tpz

Результат:

Вывод
21 true

На первом шаге заполнителя нет, поэтому сохранённая 5 вставляется первым аргументом: получается add(5, 2). На втором шаге место сохранённой 7 указано явно: multiply(7, 3). В последнем конвейере оба _ получают одно и то же сохранённое значение 21, поэтому вызов равнозначен equal(21, 21). Левая часть не вычисляется повторно ради второго заполнителя.

Четыре формы правой части

Правая частьЗначение
value |> call(other)Вставить value перед всеми явными позиционными, развёрнутыми и именованными аргументами
value |> call(_, other)Заменить каждый допустимый _ на value, не добавляя ещё один аргумент
value |> callableВызвать вызываемое значение с единственным аргументом value
value |> .fieldПрочитать field у value

Конвейеры связываются слева направо: каждый шаг получает завершённый результат предыдущего. Заполнитель относится к ближайшему содержащему его вызову. Символ _ в шаблоне сопоставления, напротив, означает пропуск значения; токен одинаков, но область и назначение различаются.

В позициях аргументов одного вызова разрешён один или несколько заполнителей. Все они получают одно сохранённое левое значение. Если справа присутствует хотя бы один допустимый _, замена имеет приоритет и дополнительная вставка первого аргумента не выполняется.

Частая ошибка

Сам по себе _ не является значением. Его нельзя поставить всей правой частью, использовать как вызываемый объект, имя члена или поле. Поместите его в список аргументов того вызова, который должен получить значение конвейера.

Сокращение value |> ?.field не поддерживается. Используйте обычную опциональную цепочку заранее или явную лямбду. Именованные аргументы и после подстановки должны идти за позиционными и развёрнутыми. Если правая часть не является вызовом, вызываемым значением или .field, проверка сообщает статическую ошибку.

Конвейер не добавляет автоматическую передачу Result, частичное применение или неявную асинхронность. Для Result используйте явный постфиксный ?, а для ограниченной конкурентной работы — явный concurrent.

Приоритет описан в Операторы и выражения, вызываемые значения — в Функции и обобщения, а этапы над коллекциями — в Коллекции и включения.