Извлечение значений из переменных: парсинг в языке PHP

Раздел: Работа с данными в PHP -> Парсинг переменных

Основные методы парсинга переменных в PHP

Как разобрать URL-кодированную строку в переменные PHP?

Функция parse_str() преобразует строку запроса (query string) в ассоциативный массив. Она принимает обязательный второй аргумент - массив, в который будут помещены результаты. Это самый быстрый способ получить параметры из URL или тела POST-запроса, если данные переданы в формате key=value&key2=value2.

$query = 'name=John&age=25&city=New+York';
parse_str($query, $output);
print_r($output);

Php parse var (парсинг переменных в php)

Array
(
    [name] => John
    [age] => 25
    [city] => New York
)

Второй аргумент обязателен: если его опустить, переменные будут созданы в глобальной области видимости, что устарело и считается небезопасным. Всегда передавайте массив.

Типичная проблема: если строка содержит символ & внутри значения (например, data=a&b), parse_str интерпретирует его как разделитель. Решение - экранировать амперсанд или использовать URL-кодирование (urlencode) перед формированием строки.

$value = 'a&b';
$query = 'data=' . urlencode($value); // data=a%26b
parse_str($query, $output);
echo $output['data']; // a&b

Как преобразовать JSON-строку в массив или объект?

Функция json_decode() выполняет обратное преобразование. Второй параметр true заставляет возвращать ассоциативный массив вместо объекта.

$json = '{"product":"book","price":12.5}';
$data = json_decode($json, true);
print_r($data);
Array
(
    [product] => book
    [price] => 12.5
)

При некорректном JSON возвращается null. Нужно проверять json_last_error().

$invalid = '{invalid}';
$result = json_decode($invalid);
if (json_last_error() !== JSON_ERROR_NONE) {
    echo 'Ошибка парсинга: ' . json_last_error_msg();
}

Как извлечь параметры из полного URL?

parse_url() разбирает URL на компоненты (схему, хост, путь и т.д.), а query извлекается отдельно через parse_str().

$url = 'https://example.com/page?lang=ru&page=2';
$parts = parse_url($url);
parse_str($parts['query'] ?? '', $params);
print_r($params);
Array
(
    [lang] => ru
    [page] => 2
)
Если query отсутствует, $parts['query'] не определена. Использование ?? '' предотвращает ошибку.

Как восстановить значение из сериализованной строки?

unserialize() возвращает исходное значение (массив, объект и т.д.), но представляет угрозу безопасности при работе с ненадёжными данными (возможны атаки внедрения объектов).

$serialized = 'a:2:{s:4:"name";s:4:"John";s:3:"age";i:25;}';
$data = unserialize($serialized);
print_r($data);
Array
(
    [name] => John
    [age] => 25
)
Использовать unserialize() для данных от пользователя не рекомендуется. Вместо сериализации лучше применять JSON.

Как разбить строку на части по заданному разделителю?

explode() возвращает массив фрагментов. Вместе с list() можно присвоить части отдельным переменным.

$csv = 'apple,banana,cherry';
list($first, $second, $third) = explode(',', $csv);
echo "$first, $second, $third";
apple, banana, cherry
Если количество элементов меньше числа переменных в list(), будет ошибка уровня E_WARNING (начиная с PHP 8.0) и недостающие переменные получат значение null. Проверяйте число элементов с count().

Как извлечь данные по регулярному выражению?

preg_match() находит первое совпадение и помещает его в массив $matches.

$text = 'Артикул: ABC-123, цена: 450 руб.';
preg_match('/Артикул:\s*([A-Z]+-\d+)/', $text, $matches);
echo $matches[1];
ABC-123
Шаблон должен быть аккуратным; неэкранированные спецсимволы могут вызвать ошибки. Используйте модификаторы (например, /u для Юникода).

Как проверить и очистить данные определённого типа?

filter_var() с флагом FILTER_VALIDATE_* или FILTER_SANITIZE_* позволяет парсить и фильтровать одно значение.

$email = 'user@example.com';
if (filter_var($email, FILTER_VALIDATE_EMAIL)) {
    echo 'Email корректен';
} else {
    echo 'Email некорректен';
}
Email корректен
Функция не извлекает данные из строки, а только проверяет/очищает. Для извлечения встроенных данных (например, IP из текста) она не подходит.

Выбор подходящего метода зависит от формата входных данных и требуемого уровня безопасности. Для строк запроса используйте parse_str(), для JSON - json_decode(), для произвольных строк - регулярные выражения или explode().

Расширенные примеры парсинга переменных

Многоуровневый разбор JSON с проверкой ошибок

Пример
$json = '{"user":{"name":"Анна","orders":[{"id":1,"total":200},{"id":2,"total":350}]}}';
$data = json_decode($json, true);
if (json_last_error() === JSON_ERROR_NONE) {
    foreach ($data['user']['orders'] as $order) {
        echo 'Заказ ' . $order['id'] . ': ' . $order['total'] . ' руб.<br>';
    }
} else {
    echo 'Ошибка парсинга JSON: ' . json_last_error_msg();
}
Заказ 1: 200 руб.
Заказ 2: 350 руб.

Форматированный ввод с sscanf()

sscanf() разбирает строку по шаблону, аналогичному printf, и возвращает массив значений.

Пример
$date = '2025-04-01';
$parts = sscanf($date, '%4d-%2d-%2d', $year, $month, $day);
echo "Год: $year, месяц: $month, день: $day";
Год: 2025, месяц: 4, день: 1

Разбор CSV-строки с кавычками через str_getcsv()

Встроенная функция str_getcsv() корректно обрабатывает поля, заключённые в кавычки, и экранированные запятые.

Пример
$csvLine = '"Иванов, Иван", "Петров", "Сидоров"';
$fields = str_getcsv($csvLine, ',', '"');
print_r($fields);
Array
(
    [0] => Иванов, Иван
    [1] => Петров
    [2] => Сидоров
)

Извлечение нескольких совпадений с preg_match_all()

Пример
$html = '<a href="/page1">Ссылка 1</a><a href="/page2">Ссылка 2</a>';
preg_match_all('/href="([^"]+)"/', $html, $matches);
print_r($matches[1]);
Array
(
    [0] => /page1
    [1] => /page2
)

Безопасное разбирание строки запроса с фильтрацией

Комбинация parse_str() и filter_var_array() позволяет получить только ожидаемые параметры с проверкой типа.

Пример
$query = 'name=John&age=25&extra=malicious';
parse_str($query, $raw);
$allowed = ['name' => FILTER_SANITIZE_STRING, 'age' => FILTER_VALIDATE_INT];
$filtered = filter_var_array($raw, $allowed);
print_r($filtered);
Array
(
    [name] => John
    [age] => 25
)

Параметр extra игнорируется, так как отсутствует в списке.

Работа с сериализованными объектами и __wakeup

Если необходимо безопасно десериализовать объекты только известного класса, можно реализовать белый список классов с помощью опции allowed_classes в PHP 8.0+.

Пример
class User {
    public string $name;
    public function __wakeup() {
        // дополнительная логика восстановления
    }
}
$serialized = 'O:4:"User":1:{s:4:"name";s:4:"John";}';
$user = unserialize($serialized, ['allowed_classes' => ['User']]);
if ($user instanceof User) {
    echo 'Восстановлен пользователь: ' . $user->name;
}
Восстановлен пользователь: John

При попытке десериализовать класс, не входящий в allowed_classes, будет возвращён экземпляр __PHP_Incomplete_Class.

Парсинг переменных в PHP - comments

En
Php parse var (php)