mysql pdo prepare_PHP PDO prepare()、execute()和bindParam()方法详解

每次将查询发送给MySQL服务器时,都必须解析该查询的语法,确保结构正确并能够执行。这是这个过程中必要的步骤,但也确实带来了一些开销。做一次是必要的,但如果反复地执行相同的查询,批量插入多行并只改变列值时会怎么样呢?预处理语句会在服务器上缓存查询的语法和执行过程,而只在服务器和客户端之间传输有变化的列值,以此来消除这些额外的开销。

PDO为支持此特性的数据库提供了预处理语句功能。因为MySQL支持这个特性,所以可以在适当时使用预处理语句。

预处理语句是使用两个方法实现的:prepare()方法负责准备要执行的查询,execute()方法使用一组给定的列参数反复地执行查询。这些参数可以显式地作为数组传递给execute()方法,也可以使用通过bindParam()方法指定的绑定参数提供给execute()方法。

使用预处理语句——prepare()方法

prepare()方法负责准备要执行的查询。语法格式如下:

PDOStatement PDO::prepare(string statement[,array driver_options])

但是,用作准备语句的查询与以住使用的查询略有区别,因为对于每次执行迭代中要改变的值,必须使用占位符而不是具体的列值。

查询支持两种不同的语法:命名参数和问号参数。

使用命名参数的查询如下:

INSERT INTO tb_chengji SET xuesheng=:xuesheng,yuwen=:yuwen;

其中,:xuesheng与:yuwen都是列占位符。

使用问号参数的查询如下:

INSERT INTO tb_chengji SET xuesheng=?,yuwen=?;

其中,?也是列占位符。

选择哪一种语法都可以,但是前者更明确一些。

下面使用prepare()方法准备一个用于迭代执行的查询:

$pdo=new PDO($dsn,$user,$pwd); // 连接数据库

$query="INSERT INTO tb_chengji SET xuesheng=:xuesheng,yuwen=:yuwen";

$result=$pdo->prepare($query);

?>

上面的代码将查询准备好了。继续下面的操作。

执行准备查询——execute()方法

execute()方法负责执行准备好的查询。语法格式如下:

bool PDOStatement::execute([array input_parameters])

该方法需要有每次迭代执行中替换的输入参数。这可以通过两种方法实现:作为数组将值传递给方法,或者通过bindParam()方法把值绑定到查询中相应的变量名或位置偏移。

下面介绍第一种方法,第二种方法在bindParam()方法中介绍。

实例代码中准备了一条语句并通过execute()方法反复执行,每次使用不同的参数:

$pdo=new PDO($dsn,$user,$pwd); // 连接数据库

$query="INSERT INTO tb_chengji SET xuesheng=:xuesheng,yuwen=:yuwen";

$result=$pdo->prepare($query);

$result->execute(array(':xuesheng'=>'赵天平',':yuwen'=>'90')); // 执行一次

$result->execute(array(':xuesheng'=>'张冬雪',':yuwen'=>'115')); // 再执行一次

?>

下面通过使用bindParam()方法进行绑定来传递查询参数。

绑定参数——bindParam()方法

execute()方法中的input_parameters参数是可选的,虽然很方便,但是如果需要传递多个变量时,以这种方式提供数组会很快变得难以处理(当数组元素过多时,也就是当数据表中的列过多时,代码设计会变得特别难以阅读或出错)。使用bindParam()方法可以解决这个问题。语法格式如下:

boolean PDOStatement::bindParam(mixed parameter,mixed &variable[,int datatype

[,int length[,mixed driver_options]]])

parameter:当在prepare()方法中使用命名参数时,parameter是预处理语句中使用语法(例如:xuesheng)指定的列值占位符的名字;使用问号参数时,parameter是查询中列值占位符的索引偏移。

variable:该参数存储将赋给占位符的值。它按引用传递,因为结合准备存储过程使用此方法时,可以根据存储过程的某个动作修改这个值。

datatype:该参数显式地设置参数的数据类型,可以为以下值:

PDO_PARAM_BOOL:SQL BOOLEAN类型。

PDO_PARAM_INPUT_OUTPUT:参数传递给存储过程时使用此类型,因此,可以在过程执行后修改。

PDO_PARAM_INT:SQL INTEGER数据类型。

PDO_PARAM_NULL:SQL NULL数据类型。

PDO_PARAM_LOB:SQL大对象数据类型。

PDO_PARAM_STMT:PDOStatement对象类型,当前不可操作。

PDO_PARAM_STR:SQL CHAR、VARCHAR和其它字符串数据类型。

length:该参数指定数据类型的长度。只有当赋为PDO_PARAM_INPUT_OUTPUT数据类型时才需要这个参数。

driver_options:该参数用来传递任何数据库驱动程序特定的选项。

下面修改前面的实例,使用bindParam()方法来赋列值:

$pdo=new PDO($dsn,$user,$pwd); // 连接数据库

$query="INSERT INTO tb_chengji SET xuesheng=:xuesheng,yuwen=:yuwen";

$result=$pdo->prepare($query);

$xuesheng='赵天平';

$yuwen='90';

$result->bindParam(':xuesheng',$xuesheng);

$result->bindParam(':yuwen',$yuwen);

$result->execute();

$xuesheng='张冬雪';

$yuwen='115';

$result->bindParam(':xuesheng',$xuesheng);

$result->bindParam(':yuwen',$yuwen);

$result->execute();

?>

如果使用问号参数,语句则如下所示:

$query="INSERT INTO tb_chengji SET xuesheng=?,yuwen=?";

因此对应的bindParam()方法调用如下:

$xuesheng='赵天平';

$yuwen='90';

$result->bindParam(1,$xuesheng);

$result->bindParam(2,$yuwen);

......

$xuesheng='张冬雪';

$yuwen='115';

$result->bindParam(1,$xuesheng);

$result->bindParam(2,$xuesheng);

实例

在执行下面的实例代码之前,tb_chengji数据表中的数据记录如下图所示:

4702.gif

执行下面的实例代码:

复制代码

PHP PDO prepare()、execute()和bindParam()方法详解实例-www.baike369.com

$dbms='mysql';

$dbname='db_xuesheng';

$user='root';

$pwd='1234';

$host='localhost';

$dsn="$dbms:host=$host;dbname=$dbname";

try{

$pdo=new PDO($dsn,$user,$pwd);

$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

$query="INSERT INTO tb_chengji SET xuesheng = :xuesheng,yuwen = :yuwen,shuxue = :shuxue,yingyu = :yingyu";

$result=$pdo->prepare($query);

$result->execute(array(":xuesheng"=>"周一刚",":yuwen"=>"55",":shuxue"=>"80",":yingyu"=>"78"));

$result->execute(array(":xuesheng"=>"胡伟",":yuwen"=>"107",":shuxue"=>"99",":yingyu"=>"113"));

$xuesheng="孙维维"; // 可以接受

标签传递过来的值

$yuwen="86";

$shuxue="66";

$yingyu="78";

$result->bindParam(":xuesheng",$xuesheng);

$result->bindParam(":yuwen",$yuwen);

$result->bindParam(":shuxue",$shuxue);

$result->bindParam(":yingyu",$yingyu);

$result->execute();

// 可以多次添加数据记录

$xuesheng="王萍";

$yuwen="116";

$shuxue="45";

$yingyu="69";

$result->bindParam(":xuesheng",$xuesheng);

$result->bindParam(":yuwen",$yuwen);

$result->bindParam(":shuxue",$shuxue);

$result->bindParam(":yingyu",$yingyu);

$result->execute();

}catch(Exception $exception){

echo $exception->getMessage();

}

?>

上面的实例执行一次代码,可以添加多条数据记录。当然,执行一次代码,也可以添加一条记录。

上面的实例代码,还可以写成下面的格式,效果是一样的:

复制代码

PHP PDO prepare()、execute()和bindParam()方法详解实例-www.baike369.com

$dbms='mysql';

$dbname='db_xuesheng';

$user='root';

$pwd='1234';

$host='localhost';

$dsn="$dbms:host=$host;dbname=$dbname";

try{

$pdo=new PDO($dsn,$user,$pwd);

$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

$query="INSERT INTO tb_chengji SET xuesheng=?,yuwen=?,shuxue=?,yingyu=?";

$result=$pdo->prepare($query);

$result->execute(array("周一刚","55","80","78"));

$result->execute(array("胡伟","107","99","113"));

$xuesheng="孙维维"; // 可以接受

标签传递过来的值

$yuwen="86";

$shuxue="66";

$yingyu="78";

$result->bindParam(1,$xuesheng);

$result->bindParam(2,$yuwen);

$result->bindParam(3,$shuxue);

$result->bindParam(4,$yingyu);

$result->execute();

// 可以多次添加数据记录

$xuesheng="王萍";

$yuwen="116";

$shuxue="45";

$yingyu="69";

$result->bindParam(1,$xuesheng);

$result->bindParam(2,$yuwen);

$result->bindParam(3,$shuxue);

$result->bindParam(4,$yingyu);

$result->execute();

}catch(Exception $exception){

echo $exception->getMessage();

}

?>

执行实例代码以后,tb_chengji数据表中的数据记录如下图所示:

4701.gif

提示

当使用PHP中PDO的prepare()、execute()和bindParam()方法时,网页的编码一定要设置为utf-8:

否则,将不能输入中文汉字数据。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,下面是一个简单的 emp_edit.php 页面实现,用于编辑员工信息: ```php <?php // 数据库连接参数 $host = "localhost"; $username = "root"; $password = "123456"; $dbname = "itcast"; // 连接数据库 $db = new PDO("mysql:host={$host};dbname={$dbname}", $username, $password); // 处理编辑请求 if ($_SERVER['REQUEST_METHOD'] == 'POST') { $id = $_POST['id']; $name = $_POST['name']; $gender = $_POST['gender']; $hire_date = $_POST['hire_date']; $address = $_POST['address']; $phone = $_POST['phone']; // 更新员工信息 $sql = "UPDATE employees SET name=:name, gender=:gender, hire_date=:hire_date, address=:address, phone=:phone WHERE id=:id"; $stmt = $db->prepare($sql); $stmt->bindParam(':id', $id); $stmt->bindParam(':name', $name); $stmt->bindParam(':gender', $gender); $stmt->bindParam(':hire_date', $hire_date); $stmt->bindParam(':address', $address); $stmt->bindParam(':phone', $phone); $stmt->execute(); // 跳转回员工列表页面 header('Location: employees.php'); exit(); } // 获取员工信息 $id = $_GET['id']; $sql = "SELECT * FROM employees WHERE id=:id"; $stmt = $db->prepare($sql); $stmt->bindParam(':id', $id); $stmt->execute(); $employee = $stmt->fetch(PDO::FETCH_ASSOC); ?> <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>编辑员工信息</title> </head> <body> <h1>编辑员工信息</h1> <form method="post"> <input type="hidden" name="id" value="<?php echo $employee['id']; ?>"> <p> <label for="name">姓名:</label> <input type="text" id="name" name="name" value="<?php echo $employee['name']; ?>"> </p> <p> <label for="gender">性别:</label> <input type="radio" id="male" name="gender" value="男"<?php if ($employee['gender'] == '男') echo ' checked'; ?>> <label for="male">男</label> <input type="radio" id="female" name="gender" value="女"<?php if ($employee['gender'] == '女') echo ' checked'; ?>> <label for="female">女</label> </p> <p> <label for="hire_date">入职日期:</label> <input type="date" id="hire_date" name="hire_date" value="<?php echo $employee['hire_date']; ?>"> </p> <p> <label for="address">地址:</label> <input type="text" id="address" name="address" value="<?php echo $employee['address']; ?>"> </p> <p> <label for="phone">电话:</label> <input type="text" id="phone" name="phone" value="<?php echo $employee['phone']; ?>"> </p> <p> <button type="submit">保存</button> <button type="button" onclick="location.href='employees.php'">取消</button> </p> </form> </body> </html> ``` 这里我们首先判断请求的方法是否为 POST,如果是 POST,则获取提交的员工信息,并更新数据库中对应的记录,然后跳转回员工列表页面。如果不是 POST,则根据传递过来的员工 id,获取员工信息并显示在表单中。在表单中,我们使用了 input type="hidden" 来隐藏员工的 id,方便后续进行更新操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值