PHP вызывает функцию с переменным количеством параметров - PullRequest
1 голос
/ 26 февраля 2010

Так что я столкнулся с небольшой проблемой. Я знаю решение, но оно не кажется очень чистым, и мне интересно, есть ли лучшее.

Я пишу оболочку MySQLi для запуска подготовленных операторов. Поскольку он является оберткой и предназначен для повторного использования (динамический) количество возвращаемых столбцов зависит от запроса и не является статическим.

Единственное решение, которое я нашел и которое, похоже, используют все, - call_user_func_array.

Это работает, но моя проблема в том, что я создаю дополнительный массив ссылок, который мне не нужен, во-первых.

Например:

<?php

// Connect, prepare statement, etc.

$stmt->execute();

$fields = $stmt->result_metadata();
$fields = $fields->fetch_fields();

foreach ($fields as $field) {
    // Unnecessary creation of an array.
    $params[] = &$row[$field->name];
}

call_user_func_array(array($stmt, 'bind_result'), $params);

?>

Так что теперь я создаю еще один массив, чтобы call_user_func_array передавал параметры по ссылке, поскольку он не соответствует определению метода.

Есть ли способ заставить call_user_func_array придерживаться определений методов / функций? Есть ли более чистый способ вызова метода / функции с переменным количеством параметров? Или, в целом, есть только более чистое и лучшее решение этой проблемы?

Я также сталкивался с подобными проблемами при вызове bind_param, пытаясь сохранить возможность изменения связанных параметров и повторного выполнения оператора без изменений.

В некотором побочном вопросе, что именно делает код ниже.

$row[$field->name] = &$row[$field->name];

Это странно работает и не выдает никаких ошибок, хотя я не совсем понимаю, как переменная может ссылаться на себя. Есть ли существенные различия между этим и первым, кроме того, что я не создаю другой массив? Это лучше?

Спасибо.

EDIT:

Так я использовал Reflection API вместо call_user_fun_array. Будем весьма благодарны за любые отзывы о моем использовании, производительности против call_user_func_array, реализации и т. Д. Я никогда не сталкивался с этим раньше, и почти все методы недокументированы, поэтому я не совсем уверен, как правильно их использовать.

<?php

foreach ($fields as $field) {
    $row[$field->name] = NULL;
}

$refMethod = new ReflectionMethod($stmt, 'bind_result');
$refMethod->invokeArgs($stmt, $row);

?>

1 Ответ

2 голосов
/ 26 февраля 2010

Один из известных мне способов заключается в том, что вы можете использовать Reflection класса isPassedByReference.

Вот решение, которое я нашел после того, как столкнулся с этой проблемой для инфраструктуры, которую я разрабатывал.

...