downloads | documentation | faq | getting help | mailing lists | licenses | wiki | reporting bugs | php.net sites | links | conferences | my php.net

search for in the

mysqli::query> <mysqli::poll
Last updated: Fri, 14 Aug 2009

view this page in

mysqli::prepare

mysqli_prepare

(PHP 5)

mysqli::prepare -- mysqli_preparePrépare une requête SQL pour l'exécution

Description

Style orienté objet :

mysqli_stmt prepare ( string $query )

Style procédural :

mysqli_stmt mysqli_prepare ( mysqli $link , string $query )

Prépare la requête SQL query et retourne une ressource à utiliser pour les futures opérations sur le traitement. La requête doit être une requête SQL unique.

Les paramètres de marques doivent être liés à des variables utilisées dans les fonctions mysqli_stmt_bind_param() et/ou mysqli_stmt_bind_result() avant d'exécuter la requête ou de récupérer les lignes.

Liste de paramètres

link

Seulement en style procédural : Un identifiant de lien retourné par la fonction mysqli_connect() ou par la fonction mysqli_init()

query

La requête, sous la forme d'une chaîne de caractères.

Note: Vous ne devez pas ajouter de point virgule ou de \g dans la requête.

Ce paramètre peut inclure un ou plusieurs paramètres de marques dans la requête SQL avec le caractère "point d'interrogation" (?) à la position appropriée.

Note: Les marques sont autorisées uniquement dans certaines endroits des requêtes SQL. Par exemple, elles le sont dans la liste VALUES() d'une requête INSERT (pour spécifier les valeurs des colonnes pour une ligne), ou dans une comparaison d'une clause WHERE pour spécifier une valeur de comparaison.
Cependant, elles ne sont pas autorisées pour les identifiants (comme les noms de tables ou de colonnes), dans une liste de sélection où les noms des colonnes doivent être retournés par une requête SELECT, ou pour spécifier un opérateur tel que le signe égal (=). La dernière restriction est nécessaire, car il est impossible de déterminer le type de paramètre. Il n'est pas non plus autorisé de comparer les marqueurs avec NULL par ? IS NULL. En général, les paramètres ne sont autorisés que dans les requêtes DML ("Data Manipulation Language") et non dans les requêtes DDL ("Data Definition Language").

Valeurs de retour

mysqli_prepare() retourne un objet de traitement ou FALSE si une erreur survient.

Exemples

Exemple #1 Style orienté objet

<?php
$mysqli 
= new mysqli("localhost""my_user""my_password""world");

/* Vérification de la connexion */
if (mysqli_connect_errno()) {
    
printf("Échec de la connexion : %s\n"mysqli_connect_error());
    exit();
}

$city "Amersfoort";

/* Crée une requête préparée */
if ($stmt $mysqli->prepare("SELECT District FROM City WHERE Name=?")) {

    
/* Lecture des marqueurs */
    
$stmt->bind_param("s"$city);

    
/* Exécution de la requête */
    
$stmt->execute();

    
/* Lecture des variables résultantes */
    
$stmt->bind_result($district);

    
/* Récupération des valeurs */
    
$stmt->fetch();

    
printf("%s est dans le district de %s\n"$city$district);

    
/* Fermeture du traitement */
    
$stmt->close();
}

/* Fermeture de la connexion */
$mysqli->close();
?>

Exemple #2 Style procédural

<?php
$link 
mysqli_connect("localhost""my_user""my_password""world");

/* Vérification de la connexion */
if (mysqli_connect_errno()) {
    
printf("Échec de la connexion : %s\n"mysqli_connect_error());
    exit();
}

$city "Amersfoort";

/* Crée une requête préparée */
if ($stmt mysqli_prepare($link"SELECT District FROM City WHERE Name=?")) {

    
/* Lecture des marqueurs */
    
mysqli_stmt_bind_param($stmt"s"$city);

    
/* Exécution de la requête */
    
mysqli_stmt_execute($stmt);

    
/* Lecture des variables résultantes */
    
mysqli_stmt_bind_result($stmt$district);

    
/* Récupération des valeurs */
    
mysqli_stmt_fetch($stmt);

    
printf("%s est dans le district de %s\n"$city$district);

    
/* Fermeture du traitement */
    
mysqli_stmt_close($stmt);
}

/* Fermeture de la connexion */
mysqli_close($link);
?>

L'exemple ci-dessus va afficher :

Amersfoort est dans le district de Utrecht

Voir aussi



mysqli::query> <mysqli::poll
Last updated: Fri, 14 Aug 2009
 
add a note add a note User Contributed Notes
mysqli::prepare
sdepouw at NOSPAM dot com
30-Jul-2009 01:03
I don't know how obvious this was for anyone else, but if you attempt to prepare a query for a table that doesn't exist in the database the connection currently points to (or if your query is invalid in some other way, I suppose), an object will not be returned. I only noticed this after doing some digging when I kept getting a fatal error saying that my statement variable was not an set to an instance of an object (it was probably null).

Replace NOSPAM with nimblepros to e-mail me.
rafael at stiod dot com
29-Sep-2008 11:44
All data must be fetched before a new statement prepare
admin at xorath dot com
15-Aug-2007 05:39
Performance note to those who wonder. I performed a test where first of all inserted about 30,000 posts with one PK:id and a varchar(20), where the varchar data was md5-hash for the current iterator value just to fill with some data.

The test was performed on a dedicated ubuntu 7.04 server with apache2/php5/mysql5.0 running on Athlon 64 - 3000+ with 512MB of RAM. The queries where tested with a for-loop from 0 to 30000 first with:

<?php
for ( $i = 0; $i <= 30000; ++$i )
{
   
$result = $mysqli->query("SELECT * FROM test WHERE id = $i");
   
$row = $result->fetch_row();
    echo
$row[0]; //prints id
}
?>

which gave a page-load time of about 3.3seconds avarage, then with this loop:

<?php
$stmt
= $mysqli->prepare("SELECT * FROM test WHERE id = ?");
for (
$i = 0; $i <= 30000; ++$i )
{
   
$stmt->bind_param("i", $i);
   
$stmt->execute();
   
$stmt->bind_result($id, $md5);
   
$stmt->fetch();
    echo
$id;
}
$stmt->close();
?>

and the avarage page-load was lowered by 1.3sec, which means about 2.0 sec avarage! Guess the performance difference could be even greater on a more complex/larger table and more complex SQL-queries.
nom0ny at yahoo dot com
25-May-2007 07:30
It must be noted in the Description whether developers should call mysqli_stmt_close prior to executing mysqli_prepare again on the same statement variable.

Example, Script A calls mysqli_stmt_close twice:
<?php
/* Script A -- We are already connected to the database */

$stmt = mysqli_prepare($link, "INSERT INTO table VALUES (?, ?, 100)"); /* Query 1 */
mysqli_stmt_bind_param($stmt, "si", $string, $integer);
mysqli_stmt_execute($stmt);
mysqli_stmt_close($stmt); // CLOSE $stmt

$stmt = mysqli_prepare($link, "INSERT INTO table VALUES ('PHP', ?, ?)"); /* Query 2 */
mysqli_stmt_bind_param($stmt, "ii", $integer, $code);
mysqli_stmt_execute($stmt);
mysqli_stmt_close($stmt); // CLOSE $stmt

/* Script A -- Continues on... */
?>

Next, we have Script B, calling mysqli_prepare again before issuing mysqli_stmt_close on the prior statement.
<?php
/* Script B -- We are already connected to the database */

$stmt = mysqli_prepare($link, "INSERT INTO table VALUES (?, ?, 100)"); /* Query 1 */
mysqli_stmt_bind_param($stmt, "si", $string, $integer);
mysqli_stmt_execute($stmt);

$stmt = mysqli_prepare($link, "INSERT INTO table VALUES ('PHP', ?, ?)"); /* Query 2 */
mysqli_stmt_bind_param($stmt, "ii", $integer, $code);
mysqli_stmt_execute($stmt);

mysqli_stmt_close($stmt); // CLOSE $stmt

/* Script B -- Continues on... */
?>

Which method is more efficient and should be used by developers?
Adam
10-Aug-2006 10:03
The purpose of prepared statements is to not include data in your SQL statements. Including them in your SQL statements is NOT safe. Always use prepared statements. They are cleaner to use (code easier to read) and not prone to SQL injections.

Escaping strings to include in SQL statements doesn't work very well in some locales hence it is not safe.
codeFiend <aeontech at gmail dot com>
05-May-2006 09:47
Note that single-quotes around the parameter markers _will_ prevent your statement from being prepared correctly.
Ex:

<?php
$stmt
= $mysqli->prepare("INSERT INTO City (District) VALUES ('?')");
echo
$stmt->param_count." parameters\n";
?>
will print 0 and fail with "Number of variables doesn't match number of parameters in prepared statement" warning when you try to bind the variables to it.

But

<?php
$stmt
= $mysqli->prepare("INSERT INTO City (District) VALUES (?)");
echo
$stmt->param_count." parameters\n";
?>
will print 1 and function correctly.

Very annoying, took me an hour to figure this out.
Ulf Wostner
23-Jan-2006 04:53
Here is an example using bind_param and bind_result, showing iteration over a list of cities.

Note that there's some bug-potential in cases where the query returns NULL for some parameter value,
but the bind_result variables still might be bound.  So, we use a conditional to spray the spot first.

$mysqli->select_db("world");

$template = "SELECT District, CountryCode FROM City WHERE Name=?";
printf("Prepare statement from template: %s\n",  $template);

$cities = array('San Francisco', 'Lisbon', 'Lisboa', 'Marrakech', 'Madrid');
printf("Cities: %s\n", join(':', $cities));

if ($stmt = $mysqli->prepare($template)) {

   foreach($cities as $city) {
     // bind the string $city to the '?'
     $stmt->bind_param("s", $city);
     $stmt->execute();
     // bind result variables
     $stmt->bind_result($d,$cc);
     // 'Lisbon' is not found in the world.City table, but 'Lisboa' is.
     // Using a conditional we avoid putting Lisbon in California.
     if($stmt->fetch()) {
       printf("%s is in  %s, %s\n", $city, $d, $cc);
     }

   }
   $stmt->close();
}

With the conditional statement we get the desired result:

Prepare statement from template: SELECT District,CountryCode FROM City WHERE Name=?
Cities: San Francisco:Lisbon:Lisboa:Marrakech:Madrid

San Francisco is in  California, USA
Lisboa is in  Lisboa, PRT
Marrakech is in  Marrakech-Tensift-Al, MAR
Madrid is in  Madrid, ESP

But, without the conditional statement we would put Lisbon in California:

San Francisco is in  California, USA
Lisbon is in  California, USA
Lisboa is in  Lisboa, PRT
Marrakech is in  Marrakech-Tensift-Al, MAR
Madrid is in  Madrid, ESP
David Kramer
20-Dec-2005 08:50
I don't think these are good examples, because the primary use of prepared queries is when you are going to call the same query in a loop, plugging in different values each time.  For instance, if you were generating a report and needed to run the same query for each line, tweaking the values in the WHERE clause, or importing data from another system.

mysqli::query> <mysqli::poll
Last updated: Fri, 14 Aug 2009
 
 
show source | credits | stats | sitemap | contact | advertising | mirror sites