在處理大量數據插入操作時,直接使用INSERT語句循環執行效率較低。為了提高性能,可以使用mysqli::stmt_init結合bind_param()來實現預處理語句的批量執行,既能提升執行效率,也能防止SQL 注入風險。本文將通過實例講解如何高效地完成這一操作。
使用prepare + bind_param的方式相比傳統的字符串拼接方式更安全,尤其適用於動態參數較多的情境。其優勢包括:
避免SQL 注入;
避免重複編譯SQL,提高執行效率;
可讀性好,結構清晰。
我們將以一個簡單的用戶信息表users為例,其結構如下:
CREATE TABLE users (
id INT AUTO_INCREMENT PRIMARY KEY,
username VARCHAR(50),
email VARCHAR(100)
);
假設我們需要批量插入多條用戶記錄,以下是完整的PHP 實現方式:
<?php
// 數據庫連接配置
$mysqli = new mysqli("localhost", "db_user", "db_pass", "db_name");
// 檢查連接
if ($mysqli->connect_errno) {
die("連接失敗: " . $mysqli->connect_error);
}
// 初始化語句對象
$stmt = $mysqli->stmt_init();
// 準備 SQL 語句
$sql = "INSERT INTO users (username, email) VALUES (?, ?)";
if (!$stmt->prepare($sql)) {
die("預處理失敗: " . $stmt->error);
}
// 綁定參數(注意變量要是引用)
$stmt->bind_param("ss", $username, $email);
// 模擬要插入的數據
$data = [
["alice", "alice@m66.net"],
["bob", "bob@m66.net"],
["charlie", "charlie@m66.net"]
];
// 執行批量插入
foreach ($data as $row) {
$username = $row[0];
$email = $row[1];
if (!$stmt->execute()) {
echo "插入失敗: " . $stmt->error . "<br>";
}
}
$stmt->close();
$mysqli->close();
?>
雖然可以直接用$mysqli->prepare()簡寫,但使用stmt_init明確表示流程,更適用於復雜或大型項目。
bind_param綁定的是變量的引用,因此變量的值在循環中變更即可,不需要每次重新綁定。
在每次execute()後檢查返回值,能幫助我們快速定位具體哪條記錄插入失敗。
批量提交:對於大量數據插入,可分批處理(如每1000條一組);
關閉自動提交( $mysqli->autocommit(false) ),在一批處理完後統一提交事務;
使用多值插入語法(INSERT INTO ... VALUES (...), (...), ...)對比測試性能差異。
使用mysqli::stmt_init與bind_param()不僅可以提升批量插入的效率,更能增強應用的安全性和可維護性。在處理大量用戶數據或日誌記錄等場景時,這種方式尤為推薦。