Не можете передать постоянную переменную по ссылке с помощью $ stmt-> bind_param ()? - PullRequest
3 голосов
/ 25 мая 2011

Это мой фрагмент кода:

private function add_user_limit()
{
    global $mysqli;
    $stmt = $mysqli->prepare("INSERT INTO `user_limits` (user_ip, downloads_left) VALUES (?, ?)");
    $stmt->bind_param("si", $this->user_ip, DEFAULT_USER_LIMIT);
    $stmt->execute();
    if($stmt->affected_rows == 0)
        throw new Exception("Couldn't add new user to the user_limits table");
    $stmt->close();
    $this->downloads_left = DEFAULT_USER_LIMIT;
}

DEFAULT_USER_LIMIT определяется как 8, но с приведенным выше кодом я получаю эту ошибку:

Fatal error: Cannot pass parameter 3 by reference in C:\xampp\htdocs\classes\limits.class.php on line 38

Но если я сделаю это:

private function add_user_limit()
{
    global $mysqli;
    $stmt = $mysqli->prepare("INSERT INTO `user_limits` (user_ip, downloads_left) VALUES (?, ?)");
    $user_limit = DEFAULT_USER_LIMIT; // For some reason we can't pass a constant to bind_param
    $stmt->bind_param("si", $this->user_ip, $user_limit);
    $stmt->execute();
    if($stmt->affected_rows == 0)
        throw new Exception("Couldn't add new user to the user_limits table");
    $stmt->close();
    $this->downloads_left = DEFAULT_USER_LIMIT;
}

Это работает. Мне просто интересно, почему это происходит, потому что для меня это не имеет смысла. Я не вижу причин, по которым bind_param() не может принимать постоянную переменную в качестве параметра.

Спасибо!

Ответы [ 3 ]

3 голосов
/ 25 мая 2011

Проще говоря, это потому, что вы не можете передать константу по ссылке, и в этом нет никакого смысла, поскольку она неизменна.Кстати, константы не являются переменными;это прямо в названии.

0 голосов
/ 15 апреля 2015

bind_param Mysqli определяется следующим образом:

bind_param ( string $types , mixed &$var1 [, mixed &$... ] )

Объяснение

& означает, что переменная передается по ссылке, и поскольку на константы (например, DEFAULT_USER_LIMIT) в PHP нельзя ссылаться таким образом, они могут передаваться только как значения, потому что это то, что они есть.

Так что если у вас есть функция, которая обеспечивает передачу по ссылке, сначала вы должны сохранить значение константы в переменной и передать переменную (как вы это сделали ...)

Современное решение - просто используйте PDO

Если вы можете использовать интерфейс PDO и вам не нужно передавать значения по ссылке,
просто используйте PDO bindValue() + PDO в обычных случаях используется почти так же, как Mysqli.

public bool PDOStatement::bindValue ( mixed $parameter , mixed $value [, int $data_type = PDO::PARAM_STR ] )

И если вам все еще нужно пройти по ссылке, PDO также имеет bindParam()

public bool PDOStatement::bindParam ( mixed $parameter , mixed &$variable [, int $data_type = PDO::PARAM_STR [, int $length [, mixed $driver_options ]]] )
0 голосов
/ 26 мая 2011

Следующие вещи могут быть переданы по ссылке:

  • Переменные, то есть foo ($ a)
  • Новые операторы, т.е. foo (новый foobar ())
  • Ссылки, возвращаемые функцией

Никакие другие выражения не должны передаваться по ссылке, поскольку результат не определен

http://php.net/manual/en/language.references.pass.php

дополнительно * * 1016

mysqli_stmt_bind_param () требует, чтобы параметры передавались по ссылке , тогда как call_user_func_array () может принимать в качестве параметра список переменных, которые могут представлять ссылки или значения.

http://php.net/manual/en/mysqli-stmt.bind-param.php

...