What Is The Difference Between BindParam() And BindValue() In PDO?

Published November 9, 2024

Problem: Confusion Between PDO Binding Methods

When using PHP Data Objects (PDO), you might find two similar methods for binding parameters: bindParam() and bindValue(). These two functions can seem alike, which can make it hard to know which one to use in different situations.

The Solution: Timing of Variable Evaluation

BindParam(): Reference Binding

BindParam() binds a variable reference to a parameter in a prepared SQL statement. The variable's value is evaluated when the SQL statement is executed. This allows for changes to the bound variable before the statement runs.

The bound variable is evaluated when PDOStatement::execute() is called. You can modify the variable's value after binding but before execution, and the new value will be used in the query.

Example: Using BindParam() with Dynamic Values

<?php
$stmt = $pdo->prepare("INSERT INTO users (name, age) VALUES (:name, :age)");
$name = "John";
$age = 30;

$stmt->bindParam(':name', $name);
$stmt->bindParam(':age', $age);

// Change values after binding
$name = "Jane";
$age = 25;

$stmt->execute(); // This will insert "Jane" and 25, not "John" and 30
?>

BindValue(): Value Binding

BindValue() binds the current value of a variable to a parameter in a prepared SQL statement. This method uses the value of the variable at the time of binding, not at execution.

The bound value is set when PDOStatement::bindValue() is called. Changes to the original variable after this point will not affect the value used in the SQL statement when it's executed.

Practical Examples: BindParam() vs BindValue()

BindParam() in Action

Here's an example of how BindParam() works:

<?php
$stmt = $pdo->prepare("SELECT * FROM users WHERE status = :status");
$status = 'active';

$stmt->bindParam(':status', $status);

// Change the value of $status after binding
$status = 'inactive';

$stmt->execute();
?>

In this example, the query will select users with a status of 'inactive'. We set $status to 'active' at first, but changed it to 'inactive' before executing the statement. BindParam() uses the value of $status when the statement runs, not when it's bound.

Tip: Dynamic Value Updates

When using bindParam(), you can update the value of the bound variable multiple times before executing the statement. This is useful for scenarios where you need to run the same prepared statement multiple times with different values.

BindValue() in Action

Now, let's see how BindValue() works differently:

<?php
$stmt = $pdo->prepare("SELECT * FROM users WHERE role = :role");
$role = 'user';

$stmt->bindValue(':role', $role);

// Change the value of $role after binding
$role = 'admin';

$stmt->execute();
?>

In this case, the query will select users with the role 'user'. We changed $role to 'admin' after binding, but BindValue() uses the value of $role at the time of binding. The later change to $role doesn't affect the query.

These examples show how BindParam() allows for changes in values until execution, while BindValue() sets the value when binding occurs.