PHP PDO :: bindParam () типы данных .. как это работает?

Мне интересно, что объявление типа данных в bindParam() (или bindValue() ) используется для …

Я имею в виду, я думал, что если я определяю целочисленный аргумент ( PDO::PARAM_INT ), аргумент должен быть преобразован в целое число, что-то вроде

 $delete->bindParam(1, $kill, PDO::PARAM_INT); // should work like $delete->bindParam(1, (int)$kill); 

или, по крайней мере, выдать ошибку, если аргумент не относится к объявленному типу. Но это не так.

Открывая поиски, я обнаружил, что в архиве php.net:

Всем привет,

В настоящее время я работаю над PDO. Именно в функции bindParam (). Третий параметр data_type, похоже, здесь, чтобы заставить тип значения? Но когда я пытаюсь:

 $sql = "INSERT INTO produit (idproduit, nom, marque) VALUES (NULL, :nom, :marque)"; $stmt = $dbh->prepare($sql); $nom = 'Testarossa'; $marque = 'Ferrari' ; $stmt->BindValue(':marque',$marque) ; $stmt->BindParam(':nom',$nom,PDO::PARAM_INT) ; $stmt->execute(); $nom = '250 GTO' ; $stmt->execute(); ?> 

Я ожидал, что в моей базе данных будет либо PHP-ошибка, либо interger. Но в моей БД я:

22 Testarossa Ferrari 23 250 GTO Ferrari

Это означает, что он не изменился, если у меня есть третий параметр или нет. Или, может быть, я что-то упустил. Может ли кто-нибудь еще мне подружиться? Или просто кто-то сказал мне, где я могу найти информацию об этом.

С Уважением,

Cyruss

Это именно моя ситуация. Где мои мысли идут не так?

Solutions Collecting From Web of "PHP PDO :: bindParam () типы данных .. как это работает?"

В других структурах абстракции БД на других языках его можно использовать для таких вещей, как обеспечение правильного выполнения экранирования для значений внутри оболочки (для драйверов, которые не поддерживают соответствующие связанные параметры), и повышения эффективности сети, убедившись, что числа бинарный упакованный соответствующим образом (с учетом поддержки протокола). Похоже, в PDO это мало что делает.

  if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_STR && param->max_value_len <= 0 && ! ZVAL_IS_NULL(param->parameter)) { if (Z_TYPE_P(param->parameter) == IS_DOUBLE) { char *p; int len = spprintf(&p, 0, "%F", Z_DVAL_P(param->parameter)); ZVAL_STRINGL(param->parameter, p, len, 0); } else { convert_to_string(param->parameter); } } else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_INT && Z_TYPE_P(param->parameter) == IS_BOOL) { convert_to_long(param->parameter); } else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_BOOL && Z_TYPE_P(param->parameter) == IS_LONG) { convert_to_boolean(param->parameter); } 

Итак, если вы говорите, что это STR (или если вы вообще ничего не говорите, поскольку это значение по умолчанию), а внутренний тип данных – двойной, то он превратит его в строку с использованием одного метода, если он не является двойным, тогда преобразует его в строку, используя другой метод.

Если вы говорите, что это int, но это действительно bool, то он преобразует его в длинный.

Если вы говорите, что это bool, но это действительно номер, он преобразует его в истинное логическое.

Это действительно все, что я видел (быстро), глядя на источник stmt, я представляю, как только вы передадите параметры в драйвер, они могут сделать дополнительную магию. Итак, я бы предположил, что все, что у вас есть, – это немного правильное и многозначительное двусмысленность и различие между драйверами.

Поэтому я решил погрузиться в исходный код PHP, и это то, что я нашел.

static int really_register_bound_param в static int really_register_bound_param ext / pdo / pdo_stmt.c в строке 329 версии 5.2.9

 if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_STR && param->max_value_len <= 0 && ! ZVAL_IS_NULL(param->parameter)) { if (Z_TYPE_P(param->parameter) == IS_DOUBLE) { char *p; int len = spprintf(&p, 0, "%F", Z_DVAL_P(param->parameter)); ZVAL_STRINGL(param->parameter, p, len, 0); } else { convert_to_string(param->parameter); } } else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_INT && Z_TYPE_P(param->parameter) == IS_BOOL) { convert_to_long(param->parameter); } else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_BOOL && Z_TYPE_P(param->parameter) == IS_LONG) { convert_to_boolean(param->parameter); } 

Это PDO конверсий во время привязки.

  • PDO :: PARAM_STR преобразует все, что вы передаете, в строку, кроме null.
  • PDO :: PARAM_INT преобразует bools в longs
  • PDO :: PARAM_BOOL преобразует longs в bools

Вот и все. Больше ничего не преобразуется. PDO использует флаги PARAM для форматирования SQL, чтобы не использовать типы данных.

По крайней мере, один эффект PDO :: PARAM_INT имеет запросы INSERT : логические значения преобразуются в 0 или 1. Как и в

 $i = true; $stmt->bindParam(':i', $v, PDO::PARAM_INT); 

pdo_stmt.c:

  else if (PDO_PARAM_TYPE (param-> param_type) == PDO_PARAM_INT && Z_TYPE_P (параметр-> параметр) == IS_BOOL) {
         convert_to_long (парамет-> параметр);
 } 

Я попробовал то же самое с BindValue и получил тот же результат, поэтому поведение, которое вы видите, не ограничено bindParam.

 $stmt->BindValue(':marque', $marque) ; $stmt->BindValue(':nom', $nom, PDO::PARAM_INT) ; $stmt->execute(); $nom = '250 GTO'; $stmt->BindValue(':nom', $nom, PDO::PARAM_INT) ; $stmt->execute();