Domanda

Mi chiedo quale sia la dichiarazione del tipo di dati in bindParam ( ) (o bindValue () ) è utilizzato per ...

Voglio dire, ho pensato che se definissi un argomento intero ( PDO :: PARAM_INT ), l'argomento deve essere convertito in un numero intero, qualcosa come

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

o almeno genera un errore se l'argomento non è del tipo dichiarato. Ma non è così.

Cercando su Google, l'ho trovato nell'archivio php.net:

  

Ciao a tutti,

     

Attualmente sto lavorando a DOP. Esattamente   sulla funzione bindParam (). Il terzo   il parametro data_type sembra essere qui   forzare il tipo di valore? Ma   quando provo:

$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(); ?>
     

Mi aspettavo di avere un PHP   errore o un interger nel mio database.   Ma nel mio DB ho:

     

22 Testarossa Ferrari 23 250 GTO   Ferrari

     

Significa che non è cambiato se io   avere il terzo parametro o no. O   forse mi manca qualcosa. Qualcuno può   mi hai fregato di più? O semplicemente qualcuno   mi ha detto dove posso trovare informazioni   a riguardo.

     

Saluti,

     

Cyruss

Questa è esattamente la mia situazione. Dove stanno andando i miei pensieri?

È stato utile?

Soluzione

In altri framework di astrazione di DB in altre lingue, può essere utilizzato per cose come assicurarsi che si stia eseguendo la escape corretta per i valori in-lining (per i driver che non supportano i parametri di associazione corretti) e migliorare l'efficienza della rete rendendo certo che i numeri siano opportunamente impacchettati in binari (dato il supporto del protocollo). Sembra che in DOP, non faccia molto.

   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);
        }

Quindi, se dici che è un STR (o se non dici niente in quanto quello è il default) e il tipo interno dei tuoi dati è un doppio, lo trasformerà in una stringa usando un metodo, se non è un doppio quindi lo convertirà in una stringa usando un metodo diverso.

Se dici che è un int ma è davvero un bool, lo convertirà in un lungo.

Se dici che è un bool ma è davvero un numero, lo convertirà in un vero booleano.

Questo è davvero tutto ciò che ho visto (rapidamente) guardando la fonte stmt, immagino che una volta passati i parametri nel driver possano fare ulteriore magia. Quindi, immagino che tutto ciò che ottieni sia un po 'di fare il giusto e un sacco di ambiguità comportamentale e varianza tra i conducenti.

Altri suggerimenti

Quindi ho deciso di immergermi nel codice sorgente di PHP e questo è quello che ho trovato.

static int really_register_bound_param in ext / pdo / pdo_stmt.c sulla linea 329 della versione 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);
}

Queste sono le conversioni che DOP esegue durante l'associazione.

  • PDO :: PARAM_STR converte qualunque cosa tu gli dia in una stringa tranne null.
  • DOP :: PARAM_INT converte i bool in long
  • DOP :: PARAM_BOOL converte i long in bool

Questo è tutto. Nient'altro viene convertito. PDO utilizza i flag PARAM per formattare SQL per non trasmettere tipi di dati.

Esiste almeno un effetto DOP :: PARAM_INT ha sulle query INSERT : i valori booleani vengono convertiti in 0 o 1. Come in

$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(param->parameter) == IS_BOOL) {
        convert_to_long(param->parameter);
}

Ho provato la stessa cosa con BindValue e ho ottenuto lo stesso risultato, quindi il comportamento che stai vedendo non si limita a 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(); 
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top