php的pdo详解,php中的PDO使用详解

0、准备工作,创建数据表 users

CREATE DATABASE IF NOT EXISTS `test`;

USE `test`;

CREATE TABLE IF NOT EXISTS `users`(

id int unsigned auto_increment,

email varchar(255) not null default '',

password varchar(255) not null default '',

primary key(`id`)

)auto_increment=1,charset=utf8,engine=innodb;

1、数据库连接

http://php.net/manual/zh/pdo.connections.php

PDO::__construct(string $dsn[,string $username[,string $password[,array $driver_options]]] )

$driver_options 数组 长连接设置 PDO::ATTR_PERSISTENT=>true

$dsn = 'mysql://host=127.0.0.1;port=3306;dbname=test;charset=utf8'; // dsn

$user = 'root'; // 帐号

$pass = '';// 密码

$dbh = new PDO($dsn,$user,$pass);

// $dbh = new PDO($dsn,$user,$pass,[PDO::ATTR_PERSISTENT=>1]); // 长连接

var_dump($dbh);

2、执行sql语句 exec()   执行非查询语句的sql(select ...)   返回影响的行数或者false

intPDO::exec(string $statement)

// 正常的非查询操作返回影响行数

$sql = 'insert into users(email,password) value(\'qweqwe@asd.com\',\''.md5('dsfsadsafasf').'\')';

$rt = $dbh->exec($sql);

var_dump($rt); // int(1)

若执行的sql不存在语法错误的情况下slq会执行但是影响行数为0

如下代码:

// 执行查询sql语句

$sql = 'select * from users';

// 没有满足wher条件的记录 更新了0行 也就是影响了0行

$sql = 'update users set email=\'fanyilong@163.com\' where id>10000';

$rt = $dbh->exec($sql);

var_dump($rt); // int(0)

如果sql有错误返回false

// user表不存在 sql存在语法错误 返回false

$sql = 'update user set email=\'fanyilong@163.com\' where id>10000';

$rt = $dbh->exec($sql);

var_dump($rt); // bool(false)

所以判断exec是否执行成功要用严格判断 因为exec也会返回 0       $dbh->exec($sql) === false;

3、执行所有的sql        PDOStatement  query($sql)    http://php.net/manual/zh/pdo.query.php

可以执行所有类型的sql 执行成功返回PDOStatement 对象执行 若执行错误返回false

publicPDO::query(string $statement)

// 返回PDOStatement 插入更新等操作返回的不是false就是执行成功 并返回PDOStatement

$sql = 'select * from users';

$sql = 'insert into user(email,password) value(\'fanyilong_v5@cmd.net\',\''.md5('123456').'\')';

$sql = 'select * from user'; // sql执行错误 表user不存在 返回false

$rt = $dbh->query($sql);

var_dump($rt);

foreach($rt as $key=>$val){

print_r($val);

}

查询sql若执行成功返回 对象 PDOStatement (存储有查询的结果数据)  foreach可以直接对返回的对象进行遍历

执行insert update等非查询sql 执行成功返回PDOStatement

执行失败query 会返回false

4、预处理的形式执行sql     这样可防止sql注入

预处理带有占位符的sql字符串

select * from users where id>?

select * from users where id>:id

这里的 '?'    ':id'   都是占位符 预处理模式会转义这些参数防止sql注入

publicPDO::prepare(string $statement[,array $driver_options= array()] )

$sql = 'select * from users where id>:id';

$stmt = $dbh->prepare($sql);

var_dump($stmt);

下面的方法是 PDOStatement类的:

绑定参数到占位符

boolPDOStatement::bindValue($parameter,$value[,int $data_type= PDO::PARAM_STR] )

boolPDOStatement::bindParam($parameter,&$variable[,int $data_type= PDO::PARAM_STR[,int $length[,$driver_options]]] )

设置查询结果的组织形式

boolPDOStatement::setFetchMode(int $mode)

执行预处理函数

boolPDOStatement::execute([array $input_parameters] )

查询执行

获取一条

PDOStatement::fetch([int $fetch_style[,int $cursor_orientation= PDO::FETCH_ORI_NEXT[,int $cursor_offset= 0]]] )

获取所有条

arrayPDOStatement::fetchAll([int $fetch_style[,$fetch_argument[,array $ctor_args= array()]]] )

示例代码:

$sql = 'select * from users where id>:id';

$stmt = $dbh->prepare($sql);

// bindPatam参数绑定形式

$id=1;

$stmt->bindParam('id',$id);

// 直接绑定

$stmt->bindValue('id',1);

$stmt->execute(); // 执行预处理sql

// 设置结果集数据形式

$stmt->setFetchMode(PDO::FETCH_ASSOC);

// 查询一条数据

$rt1 = $stmt->fetch();

// 查询全部

$rt2 = $stmt->fetchAll();

var_dump($rt1);

var_dump($rt2);

关于参数绑定:

bindValidate(key,val); 直接指定绑定的参数

a、?作为占位符的情况

$stmt = $dbh->prepare('select * from user where id>? and email!=?');

$stmt->bindValue(1,1);

$stmt->bindValue(2,'fantasy@sina.com');

$stmt->execute();

print_r($stmt->fetchAll());

?占位符在绑定的时候 bindValue第一个参数指定?的序列 这个序列从1开始(而不是从零)  bindValue(n,value) 就是将value绑定到第n个?

b、以 :field 作为占位符

$stmt = $dbh->prepare('select * from user where id>:id and email!=:email');

$stmt->bindValue('id',1);

$stmt->bindValue('email','fantasy@sina.com');

$stmt->execute();

print_r($stmt->fetchAll());

bindValue 的第一个参数是 占位符 :field 中的 field bindValue(field,value) 也就是将value绑定到占位符为 :field 的地方

c、? 与 :key 混合的形式作为占位符

$stmt = $dbh->prepare('select * from user where id>? and email!=:email');

$stmt->bindValue(1,1);

$stmt->bindValue('email','fantasy@sina.com');

$stmt->execute();

print_r($stmt->fetchAll());

这种形式会报错 : Invalid parameter number: mixed named and positional parameters

bindParam(key,$value) 绑定变量到sql中

第二个参数必须是变量的引用,像bindValue一样传递常量会报错。

php5.3以后 在函数调用传递一用变量不用加 & 符了,只用在函数定义的时候对参数进行引用声明即可

function func(&$arg){......}      func('aaa');

使用方法与bindValue类似,

$stmt = $dbh->prepare('select * from user where id>? and email!=?');

$id = 1;

$email = 'fantasy@sina.com';

$stmt->bindParam(1,$id);

$stmt->bindParam(2,$email);

$stmt = $dbh->prepare('select * from user where id>:id and email!=:email');

$id = 1;

$email = 'fantasy@sina.com';

$stmt->bindParam('id',$id);

$stmt->bindParam('email',$email);

execut绑定参数 execut(args_array)

在两种不同的占位符的情况下的绑定形式如下:

?占位符

$stmt = $dbh->prepare('select * from user where id>? and email!=?');

$stmt->execute([1,'fantasy@sina.com']);

print_r($stmt->fetchAll());

:field 占位符

$stmt = $dbh->prepare('select * from user where id>:id and email!=:email');

$stmt->execute(['id'=>1,'email'=>'fantasy@sina.com']);

print_r($stmt->fetchAll());

非常值得注意的一点是 bindParam() 的一个坑就是 这个函数第二个参数是引用,在foreach循环调用的时候会出现一个bug

当我们这样使用bindParam的时候

$stmt=$dbh->prepare('select * from users where title=:title and name=:name');

$params = [':title'=>'head of artical',':name'=>'fantasy'];

foreach($params as $key=>$val){

$stmt->bindParam($key,$val);

}

这样绑定的结果是 select * from users where title='fantasy' and name='fantasy';

分析原因 bindParam 的第二个参数是引用型变量

分解上面的foreach 相当于:

$val = $params[':id'];

$dbh->bindParam(':id',&$val);

$val = $params[':name'];

$dbh->bindParam(':name',&$val);

同一个变量 $val 分别绑定到了 id 与 name 并且第三行修改了 $val内存中的值 这样 绑定参数的两处值也会因此改变为 第三行修改到的值

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值