Preg replace callback: примеры (PHP)
preg_replace_callback(string|array $pattern, callable $callback, string|array $subject, int $limit = -1, int &$count = null, int $flags = 0): string|array|nullФункция preg_replace_callback
Функция preg_replace_callback в PHP выполняет поиск и замену текста с использованием регулярных выражений, где замена определяется результатом выполнения пользовательской callback-функции. Она применяется, когда замена зависит от найденных совпадений и требует дополнительной обработки.
Функция принимает до пяти параметров:
- pattern - строка с регулярным выражением или массив таких строк.
- callback - функция обратного вызова, которая получает массив совпадений и возвращает строку замены.
- subject - строка или массив строк, в которых выполняется замена.
- limit (необязательный) - максимальное количество замен. Значение -1 означает отсутствие ограничений.
- count (необязательный) - переменная, в которую записывается количество выполненных замен.
- flags (необязательный) - комбинация флагов: PREG_OFFSET_CAPTURE, PREG_UNMATCHED_AS_NULL.
Простые примеры использования
<?php
$text = 'Цена: 100 и 200 долларов';
$result = preg_replace_callback('/\d+/', function($matches) {
return $matches[0] * 1.1;
}, $text);
echo $result;
?>Цена: 110 и 220 долларов
<?php
$text = 'Иванов Иван, Петров Петр';
$result = preg_replace_callback('/(?P<last>\w+)\s+(?P<first>\w+)/',
function($matches) {
return $matches['first'] . ' ' . $matches['last'];
},
$text
);
echo $result;
?>Иван Иванов, Петр Петров
Альтернативные функции PHP
Выполняет простую замену по регулярному выражению без callback-функции. Используется, когда замена статична или определяется шаблоном.
Работает аналогично preg_replace, но возвращает только измененные элементы массива.
При сложной логике обработки иногда применяется комбинация preg_match_all и ручной обработки результатов.
Распространенные ошибки
<?php
$text = 'Пример текста';
// Неправильно: передана строка вместо callable
$result = preg_replace_callback('/\w+/', 'несуществующая_функция', $text);
?>Warning: preg_replace_callback(): The callback is not callable
<?php
$text = 'Числа: 1, 2, 3';
$sum = 0;
$result = preg_replace_callback('/\d+/', function($matches) use (&$sum) {
$sum += $matches[0]; // Побочный эффект
return $matches[0];
}, $text);
// $sum теперь содержит 6
?>Числа: 1, 2, 3 (но $sum = 6)
Изменения в новых версиях PHP
Добавлена возможность использовать стрелочные функции для callback, что упрощает запись.
Улучшена обработка ошибок при некорректных регулярных выражениях - теперь выбрасывается исключение TypeError.
Добавлена поддержка флага PREG_UNMATCHED_AS_NULL для более последовательного поведения с несовпадающими группами.
Расширенные примеры
<?php
function processMarkdown($text) {
$pattern = '/\[([^\[\]]+)\]\(([^)]+)\)/';
return preg_replace_callback($pattern,
function($matches) {
return '<a href="' . htmlspecialchars($matches[2]) . '">'
. htmlspecialchars($matches[1]) . '</a>';
},
$text
);
}
$markdown = 'Ссылка [пример](https://example.com) в тексте';
echo processMarkdown($markdown);
?>Ссылка <a href="https://example.com">пример</a> в тексте
<?php
$text = '{{a{{b}}c}}';
$count = 0;
while (preg_match('/\{\{[^{}]*\}\}/', $text) && $count < 5) {
$text = preg_replace_callback('/\{\{([^{}]*)\}\}/',
function($matches) {
return '[' . strtoupper($matches[1]) . ']';
},
$text
);
$count++;
}
echo $text;
?>[A[B]C]
Аналоги в других языках
Preg replace callback в Javascript
let text = 'Цена: 100 и 200 долларов';
let result = text.replace(/\d+/g, (match) => match * 1.1);
console.log(result);Цена: 110 и 220 долларов
Preg replace callback в Python
import re
text = 'Цена: 100 и 200 долларов'
result = re.sub(r'\d+', lambda m: str(int(m.group()) * 1.1), text)
print(result)Цена: 110.0 и 220.0 долларов