博客列表 >【ThinkPHP框架】表达式查询、聚合查询、数据集处理、Model模型创建设置等操作详解

【ThinkPHP框架】表达式查询、聚合查询、数据集处理、Model模型创建设置等操作详解

 一纸荒凉* Armani
 一纸荒凉* Armani原创
2021年05月28日 14:49:131028浏览

十二、表达式查询

  • 表达式是 SQL 语句的条件
  • 表达式不分大小写
  • 表达式写在 where 里中间参数
表达式 含义 查询方法
= 等于
<> 不等于
> 大于
>= 大于等于
< 小于
<= 小于等于
[not] like 模糊查询 whereLike/whereNotLike
[not] between (不在)区间查询 whereBetween/whereNotBetween
[not] in (不在)IN 查询 whereIn/whereNotIn
[not] null 查询字段是否(不)是 NULL whereNull/whereNotNull

高级查询:https://www.kancloud.cn/manual/thinkphp6_0/1037566

1、表达式查询

  • where方法在链式操作方法里面是最常用的方法,可以完成包括普通查询、表达式查询、快捷查询、区间查询、组合查询在内的条件查询操作
  1. # 等于(=) 默认不写就是等于
  2. // 查询status等于1的博客文章
  3. // $select = Db::table('boke')->where('status',1)->select();
  4. $select = Db::table('boke')->where('status','=',1)->select();
  5. print_r($select);

  1. # 不等于(<>)
  2. // 先将id为6的文章status改为0
  3. Db::name('boke')->save(['id'=>6,'status'=>0]);
  4. // 查询status不等于1的文章列表
  5. $select = Db::name('boke')
  6. ->where('status','<>',1)
  7. ->select();
  8. echo "<pre>";
  9. print_r($select);

  1. # 大于(>)
  2. // 查询id大于8的文章列表
  3. $select = Db::table('boke')->where('id','>','8')->select();
  4. print_r($select);
  5. # 大于等于(>=)
  6. $select = Db::table('boke')->where('id','>=','3')->select();
  7. print_r($select);

  1. # 小于(<)
  2. $select = Db::table('boke')->where('id','<','5')->select();
  3. print_r($select);
  4. # 小于等于(<=)
  5. $select = Db::table('boke')->where('id','<=','5')->select();
  6. print_r($select);
  1. # 多where条件
  2. // id大于3且小于6的记录 4 5
  3. $select = Db::table('boke')
  4. ->where('id','>','3')
  5. ->where('id','<','6')
  6. ->select();
  7. print_r($select);

  1. # LIKE 模糊查询 %代表一个或多个字符 *代表一个字符
  2. // 查询标题中含有‘课程’的记录
  3. $select = Db::table('boke')->where('title','like','%课程%')->select();
  4. print_r($select);
  5. # NOT LIKE 不包含玉女心经的记录
  6. $select = Db::table('boke')->where('title','not like','%玉女心经%')->select();
  7. print_r($select);

  1. # BETWEEN 在~之间的记录
  2. // 查询id为6到10的记录
  3. $select = Db::table('boke')->where('id','between','6,10')->select();
  4. print_r($select);
  5. # NOT BETWEEN 不在~之间的记录
  6. // 查询id为6到10以外的所有记录
  7. $select = Db::table('boke')->where('id','not between',[6,10])->select();
  8. print_r($select);
  1. # IN 查询id为6,7,10的记录
  2. $select = Db::table('boke')->where('id','in','4,7,10')->select();
  3. print_r($select);
  4. # NOT IN 查询id不为为6,7,10的所有记录
  5. $select = Db::table('boke')->where('id','not in',[4,7,10])->select();
  6. print_r($select);
  1. # NULL 注意:空字符不为null
  2. $select = Db::table('boke')->where('img',null)->select();
  3. print_r($select);
  4. # NOT NULL
  5. $select = Db::table('boke')->where('img','not null')->select();
  6. print_r($select);

2、快捷查询方法

功能和上述表达式查询一致,只是将其中查询表达式换成了对应的查询关键字

  1. # LIKE
  2. $select = Db::table('boke')->whereLike('title','%玉女心经%')->select();
  3. print_r($select);
  4. # NOT LIKE
  5. $select = Db::table('boke')->whereNotLike('title','%玉女心经%')->select();
  6. print_r($select);
  7. # BETWEEN
  8. $select = Db::table('boke')->whereBetween('id','6,10')->select();
  9. print_r($select);
  10. # NOT BETWEEN
  11. $select = Db::table('boke')->whereNotBetween('id',[6,10])->select();
  12. print_r($select);
  13. # IN
  14. $select = Db::table('boke')->whereIn('id',[6,10])->select();
  15. print_r($select);
  16. # NOT IN
  17. $select = Db::table('boke')->whereNotIn('id',[6,10])->select();
  18. print_r($select);
  19. # NULL
  20. $select = Db::table('boke')->whereNull('img')->select();
  21. print_r($select);
  22. # NOT NULL
  23. $select = Db::table('boke')->whereNotNull('img')->select();
  24. print_r($select);

十三、whereOr

  1. // whereOr 两个条件满足其中一个即可
  2. // 查询id=7或6的记录,这两条记录都会被查询出来
  3. $select = Db::table('boke')->where('id','=',7)->whereOr('id','=',6)->select();
  4. print_r($select);

  1. // id<3或id>13
  2. $select = Db::table('boke')->where('id','<',3)->whereOr('id','>',13)->select();
  3. print_r($select);
  4. // id<3或num>100
  5. $select = Db::table('boke')->where('id','not in',[4,7,10])->whereOr('num','>',100)->select();
  6. print_r($select);
  7. // id>13或标题中包含玉女心经
  8. $select = Db::table('boke')->where('id','>',13)->whereOr('title','like','%玉女心经%')->select();
  9. print_r($select);

十四、数组条件

  1. // and 都要满足
  2. // id小于7并且cat为2
  3. $select = Db::table('boke')->where([
  4. ['id','<',7],
  5. ['cat','in',[2,4]]
  6. ])->select();
  7. print_r($select);

  1. // or 满足其一即可
  2. $select = Db::table('boke')->whereOr([
  3. ['id','<',7],
  4. ['id','>',13]
  5. ])->select();
  6. print_r($select);

十五、聚合查询

  • 聚合方法查询后:没有数据,返回 0,聚合查询可以配合查询条件
方法 功能
count 统计数量,参数是要统计的字段名(可选)
max 获取最大值,参数是要统计的字段名(必须)
min 获取最小值,参数是要统计的字段名(必须)
avg 获取平均值,参数是要统计的字段名(必须)
sum 获取总数,参数是要统计的字段名(必须)
  1. // 统计数量,参数是要统计的字段名(可选)
  2. $select = Db::table('boke')->count();
  3. print_r($select);
  4. // 获取最大值,参数是要统计的字段名(必须)
  5. $select = Db::table('boke')->max('num');
  6. print_r($select);
  7. // 获取最小值,参数是要统计的字段名(必须)
  8. $select = Db::table('boke')->min('num');
  9. print_r($select);
  10. // 获取平均值,参数是要统计的字段名(必须)
  11. $select = Db::table('boke')->avg('num');
  12. print_r($select);
  13. // 获取总数,参数是要统计的字段名(必须)
  14. $select = Db::table('boke')->sum('num');
  15. print_r($select);

十六、博客实战

  1. namespace app\controller;
  2. use app\BaseController;
  3. use think\facade\Db;
  4. use think\facade\View;
  5. use think\facade\Request;
  6. class Index extends BaseController
  7. {
  8. public function index(){
  9. $cat = Db::table('cat')->select();
  10. $p = input('get.p',1);
  11. $c = input('get.c',0);
  12. $t = input('get.t','');
  13. /*if($c != 0){
  14. $count = Db::table('boke')
  15. ->where('status',1)->where('cat',$c)
  16. ->count();
  17. $select = Db::table('boke')
  18. ->where('status',1)->where('cat',$c)
  19. ->page($p,$num)->order('date desc')
  20. ->select()->toArray();
  21. }else if(!empty($t)){
  22. $count = Db::table('boke')
  23. ->where('status',1)->where('title',$t)
  24. ->count();
  25. $select = Db::table('boke')
  26. ->where('status',1)->where('title','like','%'.$t.'%')
  27. ->page($p,$num)->order('date desc')
  28. ->select()->toArray();
  29. }else{
  30. $count = Db::table('boke')
  31. ->where('status',1)->count();
  32. $select = Db::table('boke')
  33. ->where('status',1)->page($p,$num)
  34. ->order('date desc')->select()->toArray();
  35. }*/
  36. // 利用数组条件简化之前的三次重复查询操作
  37. $where[] = ['status','=',1];
  38. if($c != 0){
  39. $where[] = ['cat','=',$c];
  40. }else if(!empty($t)){
  41. $where[] = ['title','like','%'.$t.'%'];
  42. }
  43. /*$where = [
  44. ['status','=',1],
  45. ['cat','=',$c],
  46. ['title','like','%'.$t.'%']
  47. ];*/
  48. $count = Db::table('boke')->where($where)->count();
  49. $select = Db::table('boke')->where($where)
  50. ->page($p,10)->order('date desc')
  51. ->select()->toArray();
  52. View::assign([
  53. 'p' => $p,
  54. 'c' => $c,
  55. 't' => $t,
  56. 'cat' => $cat,
  57. 'select' => $select,
  58. 'count' => ceil($count/10)
  59. ]);
  60. return View::fetch('index');
  61. }
  62. }

十七、其他链式操作

https://www.kancloud.cn/manual/thinkphp6_0/1037538

连贯操作 作用 支持的参数类型
alias 用于给当前数据表定义别名 字符串
strict 用于设置是否严格检测字段名是否存在 布尔值
group 用于对查询的 group 支持 字符串
having 用于对查询的 having 支持 字符串
join* 用于对查询的 join 支持 字符串和数组
union* 用于对查询的 union 支持 字符串、数组和对象
distinct 用于查询的 distinct 支持 布尔值
lock 用于数据库的锁机制 布尔值
cache 用于查询缓存 支持多个参数
comment 用于 SQL 注释 字符串
force 用于数据集的强制索引 字符串
partition 用于设置分区信息 数组 字符串
failException 用于设置没有查询到数据是否抛出异常 布尔值
sequence 用于设置自增序列名 字符串
replace 用于设置使用 REPLACE 方式写入 布尔值
extra 用于设置额外查询规则 字符串
duplicate 用于设置 DUPLCATE 信息 数组 字符串
procedure 用于设置当前查询是否为存储过程查询 布尔值
master 用于设置主服务器读取数据 布尔值
view* 用于视图查询 字符串、数组

join连表查询 文章表和分类表

  1. // 主要select返回的是对象,需要转换为数组才可以修改
  2. $select = Db::table('boke')
  3. ->where('status',1)
  4. ->order('date desc')
  5. ->select()
  6. ->toArray();
  7. // 根据文章表中的分类id查询出分类名称
  8. foreach ($select as &$value) {
  9. $catname = Db::table('cat')
  10. ->field('name')
  11. ->where('id',$value['cat'])
  12. ->find();
  13. $value['catname'] = $catname['name'];
  14. }

  1. $select = Db::table('boke a')
  2. ->where('a.status','=',1)
  3. ->field('a.*,c.name')
  4. ->join(['cat'=>'c'],'a.cat=c.id')
  5. ->select();
  6. print_r($select);
  7. $select = Db::table('boke')
  8. ->alias('a')
  9. ->field('a.*,c.name catname')
  10. ->where('a.status','=',1)
  11. ->order('a.id desc')
  12. ->join(['cat'=>'c'],'a.cat=c.id')
  13. ->select();
  14. print_r($select);

十八、原生 MySQL执行

Db类支持原生SQL查询操作,主要包括下面两个方法:

https://www.kancloud.cn/manual/thinkphp6_0/1037570

  • query 方法:查询
  1. $select = Db::query("select * from boke");
  2. print_r($select);
  3. $select = Db::query('SELECT * FROM boke WHERE `id` < 5 and `id`>=3');
  4. print_r($select);
  5. // 参数绑定
  6. $select = Db::query('SELECT * FROM boke WHERE `id` < :id', ['id' => 5]);
  7. print_r($select);
  8. Db::query("select * from boke where id=? AND status=?", [8, 1]);
  9. // 命名绑定
  10. Db::execute("update boke set title=:title where id=:id", ['title' => 'thinkphp', 'id' => 1]);
  • execute 方法:添加和修改
  1. $execute = Db::execute("INSERT INTO `cat` (`id`, `name`, `sort`, `status`) VALUES (null, 'Vue', '0', '1');");
  2. print_r($execute);
  3. $execute = Db::execute("updata `boke` set status where id=1");
  • getLastsql 调试执行的 SQL 语句
  1. $select = Db::table('boke')->field('id,title')->where('status',1)->order('id desc')->select();
  2. print_r($select);
  3. // 打印上一次执行的SQL语句
  4. echo Db::getLastSql();
  5. // SELECT `id`,`title` FROM `boke` WHERE `status` = 1 ORDER BY `id` DESC
  • fetchSql 调试执行的 SQL 语句,而不执行
  1. $select = Db::table('boke')->fetchSql()->field('id,title')->where('status',1)->order('id desc')->select();
  2. // 不执行,直接输入SQL原生语句
  3. echo $select;
  4. // SELECT `id`,`title` FROM `boke` WHERE `status` = 1 ORDER BY `id` DESC

十九、数据集

只有find单条查询返回的是数组,其余select查询均返回对象,可以通过结果集进一步操作,我们如果要修改查询出的数据,需要通过toArray()转换为数组才可以修改,其余操作无需转换也可以当做数组循环渲染。

编号 方法 描述
1 isEmpty 是否为空
2 toArray 转换为数组
3 all 所有数据
4 merge 合并其它数据
5 diff 比较数组,返回差集
6 flip 交换数据中的键和值
7 intersect 比较数组,返回交集
8 keys 返回数据中的所有键名
9 pop 删除数据中的最后一个元素
10 shift 删除数据中的第一个元素
11 unshift 在数据开头插入一个元素
12 push 在结尾插入一个元素
13 reduce 通过使用用户自定义函数,以字符串返回数组
14 reverse 数据倒序重排
15 chunk 数据分隔为多个数据块
16 each 给数据的每个元素执行回调
17 filter 用回调函数过滤数据中的元素
18 column 返回数据中的指定列
19 sort 对数据排序
20 order 指定字段排序
21 shuffle 将数据打乱
22 slice 截取数据中的一部分
23 map 用回调函数处理数组中的元素
24 where 根据字段条件过滤数组中的元素
25 whereLike Like 查询过滤元素
26 whereNotLike Not Like 过滤元素
27 whereIn IN 查询过滤数组中的元素
28 whereNotIn Not IN 查询过滤数组中的元素
29 whereBetween Between 查询过滤数组中的元素
30 whereNotBetween Not Between 查询过滤数组中的元素
  1. $select = Db::table('boke')->where('id','>=',13)->select()->toArray();
  2. print_r($select);
  3. $select = Db::table('boke')->where('id','>=',100)->select();
  4. // 原生的empty只能判断数组,不转换数组的话,空对象无法用这个判断。
  5. // 未查询出数据,空对象中有一个空数组
  6. if(empty($select)){
  7. echo '未查询到数据';
  8. }else{
  9. echo '查询到数据';
  10. }
  11. if($select->isEmpty()){
  12. echo '未查询到数据';
  13. }else{
  14. print_r($select->toArray());
  15. }
  16. // 将取出的数据进行打乱 比如随机文章
  17. print_r($select->shuffle()->toArray());

二十、事务操作

为什么要有事务呢,举个例子来说,你的账户有 100 元,现在想给朋友转账 100 元。其中就会包含两个很重要的操作,你的账户减 100 元,朋友账户多 100 元。由于转账过程中出现失败是很常见的,假设操作不包含在事务内,你的账户减钱操作成功,朋友账户加钱操作失败。就会出现,你的账户扣钱,对方没有收到钱的情况。

再比如,在发起转账操作时,由于系统需要进行像查询余额,计算,更新余额的操作,如果在等待时间内,又发起了转账操作,但目前更新余额的操作还没有成功,就会出现你的 100 元,可以给别人转账多次的情况,这对于银行来说是肯定不允许的。

简单的来说,事务就是允许有反悔的机会,一旦某个环节出现错误,可以恢复原始的状态。

对于一个事务来说通常要满足四个特性,也就是通常所说的 ACID:

  • Atomicity - 保证在一个工作单元(就是一组操作)中所有的操作都执行成功,否则的话当前这个事务就会失败,之前的操作都被会回滚。
  • Consistency - 保证一个事务被成功提交后,数据库的状态是从一致性状态变成另一个一致性状态。比如 A 给 B 转 100 元,只会出现 A 账户减 100,B 账户加 100 或者转账失败的情况,不会出现其他的状态。
  • Isolation - 保证每个事务中的操作时是独立的,对于其他事务没有影响。
  • Durability - 对于已经提交的事务,即使在数据库损坏的情况下,也不会造成数据的丢失和损坏。

更多介绍:https://www.cnblogs.com/michael9/p/11958199.html

  • 开启事务(start transaction)
  • 执行sql操作(普通sql操作)
  • 提交/回滚(commit/rollback)
  • 设置保存点 savepoint 保存点名称
  • 回滚到具体的保存点 rollback to 保存点名称

  • InnoDB引擎支持事务处理,MyISAM不支持事务处理

  1. // 启动事务 (如果下面的代码出错了,就返回到这里。)
  2. Db::startTrans();
  3. // 插入分类表。
  4. $id = Db::table('cat')->insertGetId(['name'=>'Bootstrap']);
  5. if(empty($id)){
  6. // 回滚事务,如果失败,就返回原点,返回原点的方法:rollback
  7. Db::rollback();
  8. }
  9. echo $id;
  10. // 由于id已经存在插入数据会失败
  11. // 所以前面的插入的分类数据也不会被插入
  12. $boke = Db::table('boke')->insert([
  13. 'id' => 1,
  14. 'title' => '插入失败',
  15. 'img' => '',
  16. 'content' => '',
  17. ]);
  18. if(empty($boke)){
  19. // 回滚事务,如果失败,就返回原点,返回原点的方法:rollback
  20. Db::rollback();
  21. }
  22. // 都成功了。那就没问题了。
  23. // 必须提交事务:commit
  24. // 提交事务
  25. Db::commit();

  • transaction 方法操作数据库事务,当闭包中的代码发生异常会自动回滚
  1. Db::transaction(function () {
  2. $id = Db::table('cat')->insertGetId(['name'=>'Bootstrap']);
  3. echo $id;
  4. $boke = Db::table('boke')->insert([
  5. 'title' => '',
  6. 'img' => '',
  7. 'content' => '',
  8. 'date' => '212'
  9. ]);
  10. echo $boke;
  11. });

二十一、模版分页

https://www.kancloud.cn/manual/thinkphp6_0/1037638

https://my.oschina.net/u/3470006/blog/3112782

  • paginate 内置了分页实现,要给数据添加分页输出功能变得非常简单
  • raw 不使用(默认)转义
  • render 获取分页显示
  • total 获取总数量
  1. namespace app\controller;
  2. use app\BaseController;
  3. use think\facade\Db;
  4. use think\facade\View;
  5. use think\facade\Request;
  6. class Index extends BaseController
  7. {
  8. public function index(){
  9. $cat = Db::table('cat')->select();
  10. $c = input('get.c',0);
  11. $t = input('get.t','');
  12. $where[] = ['status','=',1];
  13. if($c != 0){
  14. $where[] = ['cat','=',$c];
  15. }else if(!empty($t)){
  16. $where[] = ['title','like','%'.$t.'%'];
  17. }
  18. $select = Db::table('boke')->where($where)->paginate(10);
  19. $page = $select->render();
  20. $total = $select->total();
  21. View::assign([
  22. 'c' => $c,
  23. 't' => $t,
  24. 'cat' => $cat,
  25. 'select' => $select,
  26. 'page' => $page
  27. ]);
  28. return View::fetch('index');
  29. }
  30. }

view 视图

  1. // 这两种方式都可以渲染分页列表
  2. // 第一种是用模版函数直接渲染传递过来的数据 {$select|raw}
  3. // 第二种是控制器中通过render方法获取的分页html代码 $page = $select->render();
  4. <ul class="pagination">
  5. {$select|raw}
  6. {$page|raw}
  7. </ul>
编号 方法 描述
1 list_rows 是否为空
2 page 当前页
2 path url 路径
2 query url 额外参数
2 fragment url 锚点
2 var_page 分页变量
  1. <?php
  2. namespace app\controller;
  3. use app\BaseController;
  4. use think\facade\View;
  5. use think\facade\App;
  6. use think\facade\Db;
  7. class Index extends BaseController
  8. {
  9. public function index()
  10. {
  11. // 获取分类ID
  12. $c = input('get.c',0);
  13. // 获取搜索内容
  14. $t = input('get.t',null);
  15. // 每页显示条数
  16. $num = 6;
  17. // 查询出分类列表
  18. $cat = Db::name('cat')->where('status',1)->order('sort desc')->select();
  19. // 查询前四条热门文章列表
  20. $hot = Db::table('boke')->field('id,title')->limit(4)->order('num','asc')->select();
  21. $where[] = ['a.status','=',1];
  22. if($c != 0){
  23. $where[] = ['a.cat','=',$c];
  24. }else if(!empty($t)){
  25. $where[] = ['a.title','like','%'.$t.'%'];
  26. }
  27. $count = Db::table('boke a')->where($where)->count();
  28. $select = Db::table('boke a')
  29. ->field('a.*,c.name catname')
  30. ->where($where)
  31. ->order('a.date desc')
  32. ->join(['cat'=>'c'],'a.cat=c.id')
  33. ->paginate([
  34. 'list_rows' => $num,
  35. 'query' => request()->param()
  36. // 'query' => [
  37. // 'c' => $c,
  38. // 't' => $t,
  39. // 'page' => input('get.page')
  40. // ]
  41. ]);
  42. View::assign([
  43. 'c' => $c,
  44. 't' => $t,
  45. 'cat' => $cat,
  46. 'select' => $select,
  47. 'hot' => $hot
  48. ]);
  49. return View::fetch('index');
  50. }
  51. }
  52. <div class="page">
  53. <nav>
  54. <ul class="pagination">
  55. {$select|raw}
  56. </ul>
  57. </nav>
  58. </div>

二十二、模型Model

  • 请确保你已经在数据库配置文件中配置了数据库连接信息
  • 模型会自动对应数据表,模型类的命名规则是除去表前缀的数据表名称,采用驼峰法命名,并*首字母大写
  • 模型自动对应的数据表名称都是遵循小写+下划线规范,如果你的表名有大写的情况,必须通过设置模型的 table 属性。

1、创建模型

模型名 数据库前缀
Boke zs_boke
Cat zs_cat
BokeComment zs_boke_comment
  1. CREATE TABLE `zs_boke_comment` (
  2. `id` int(10) unsigned NOT NULL AUTO_INCREMENT COMMENT '评论ID',
  3. `boke_id` int(10) unsigned NOT NULL DEFAULT '0' COMMENT '博客id',
  4. `comment` text NOT NULL COMMENT '评论',
  5. `add_time` int(10) unsigned NOT NULL DEFAULT '0' COMMENT '时间',
  6. PRIMARY KEY (`id`)
  7. ) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4;

表前缀设置:config/database.php 文件里 prefixzs_表前缀

  • 第一步:创建一个跟控制器平级的目录,目录名:model
  • 第二步:在 model创建 Boke.php 文件

  • 创建 model 文件:app/Model/Boke.php

  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. public function get_data(){
  5. // Db::table('zs_boke')===Db::name('boke')===Boke::===static::
  6. $select = Boke::where('id','<',7)->select();
  7. return $select;
  8. }
  9. }
  10. // 如果不设置表前缀配置,需要驼峰命名模型名称
  11. /*class ZsBoke extends Model{
  12. public function get_data(){
  13. // Db::table('zs_boke')===ZsBoke::===static::
  14. $select = ZsBoke::->select(6);
  15. return $select;
  16. }
  17. }*/

2、controller 调用 model

  1. namespace app\controller;
  2. use app\model\Boke;
  3. class Index{
  4. public function index(){
  5. $db = new Boke();
  6. $index = $db->get_data();
  7. print_r($index);
  8. }
  9. }

3、model 调用 model

  • 创建 model 文件:app/Model/Cat.php
  1. namespace app\model;
  2. use think\Model;
  3. class Cat extends Model{
  4. public function get_data(){
  5. $select = Cat::select();
  6. return $select->toArray();
  7. }
  8. }
  9. namespace app\model;
  10. use think\Model;
  11. use app\model\Cat;
  12. class Boke extends Model{
  13. public function get_data(){
  14. $cat = new Cat();
  15. $select = $cat->get_data();
  16. return $select;
  17. }
  18. }

4、模型操作

https://www.kancloud.cn/manual/thinkphp6_0/1037585

在模型中除了可以调用数据库类的方法之外(换句话说,数据库的所有查询构造器方法模型中都可以支持),可以定义自己的方法,所以也可以把模型看成是数据库的增强版

  • 模型文件里的自定义方法,不要和 thinkphp 方法一样名称
  • 模型里的Boke:: 也可以用 static:: 关键词
  • 链式操作,都可以在模型里使用

1、find查询数据

find 获取单条数据,返回的是当前模型的对象实例

  1. namespace app\model;
  2. use think\Model;
  3. class Cat extends Model{
  4. public function find(){
  5. $find = Cat::find(2);
  6. $find = static::where('id',2)->find();
  7. return $find;
  8. }
  9. }

2、select查询数据

select 获取多条数据,返回的是当前模型的对象实例

  1. public function select(){
  2. $select = Boke::select();
  3. $select = Boke::select(6);
  4. $select = static::where('id','<',7)->select();
  5. return $select;
  6. }

4、数据转换

toArray方法将当前的模型实例输出为数组

  1. public function select(){
  2. $select = Boke::select();
  3. $select = static::select(6);
  4. $select = static::where('id','<',7)->select();
  5. return $select->toArray();
  6. }

5、增加数据

  • create 静态方法添加数据,返回的是当前模型的对象实例
  1. public function create(){
  2. $create = Cat::create([
  3. 'name' => 'bootstrap',
  4. 'sort' => 0,
  5. 'status' => 1
  6. ]);
  7. echo $create->id; // 可以直接获取自增id
  8. return $create;
  9. }

新增数据的最佳实践原则:使用create方法新增数据,使用saveAll批量新增数据。

6、修改数据

  • update静态方法修改数据,返回的是当前模型的对象实例
  • save在取出数据后,更改字段更新数据。这种方式是最佳的更新方式
  1. namespace app\model;
  2. use think\Model;
  3. class Cat extends Model{
  4. public function update(){
  5. # 更新方式1
  6. $update = Cat::update(
  7. ['name'=>'响应式'],
  8. ['id'=>7]
  9. );
  10. return $update;
  11. # 更新方式2
  12. $user = Cat::find(7);
  13. $user->name = '响应式';
  14. $save = $user->save();
  15. return $save;
  16. }
  17. }

7、删除数据

  • delete静态方法删除数据,返回的是当前模型的对象实例
  • destroy 根据主键删除
  1. public function delete(){
  2. # 删除方法1
  3. $delete = Cat::where('id',3)->delete();
  4. # 删除方法2
  5. $delete = Cat::destroy(4);
  6. return $delete;
  7. }

TP模型如果只能增删查改,不如在 Controller执行了。TP模型很多特点,下面为介绍模型设置


二十三、模型设置

属性 描述
name 模型名(相当于不带数据表前后缀的表名,默认为当前模型类名)
table 数据表名(默认自动获取)
pk 主键名(默认为 id
schema 模型对应数据表字段及类型
type 模型需要自动转换的字段及类型
disuse 数据表废弃字段(数组)

1、nametable

  • 当你的数据表没有前缀的时候,name 和 table 属性的定义是没有区别的,定义任何一个即可
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $table = 'zs_boke';
  6. // 默认当前模型查询的是类名称对应的表
  7. // 也可以通过name指定其他表
  8. protected $name = 'Cat';
  9. protected $table = 'zs_cat';
  10. public function get_data(){
  11. $select = Boke::select();
  12. return $select->toArray();
  13. }
  14. }

2、pk 改变主键名称

  • 默认主键为id,如果你没有使用id作为主键名,需要在模型中设置属性:

  • 更改 id 字段名为 bid

  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. public function get_data($id=1){
  7. $find = Boke::find($id);
  8. return $find->toArray();
  9. }
  10. }

3、schema 设置模型对应数据表字段及类型

模型字段:https://www.kancloud.cn/manual/thinkphp6_0/1037581

  • 默认会自动获取(包括字段类型),但自动获取会导致增加一次查询
  • schema 属性一旦定义,就必须定义完整的数据表字段类型
  • 类型根据 php 数据类型定义,如果是 json 类型直接定义为 json 即可
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int',
  14. 'hot' => 'int',
  15. 'status' => 'int'
  16. ];
  17. # 对某个字段定义需要自动转换的类型,可以使用type属性
  18. protected $type = [
  19. 'date' => 'int'
  20. ];
  21. public function get_data(){
  22. $select = Boke::select();
  23. return $select->toArray();
  24. }
  25. }

4、disuse 数据表废弃字段(数组)

如果因为历史遗留问题 ,你的数据表存在很多的废弃字段,你可以在模型里面定义这些不再使用的字段。

  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int'
  14. ];
  15. // 统一设置不需要查询的字段名称,后续所有操作将忽略其中字段
  16. protected $disuse = [
  17. 'hot',
  18. 'status'
  19. ];
  20. public function get_data(){
  21. $select = Boke::select();
  22. return $select->toArray();
  23. }
  24. }

在查询和写入的时候会忽略定义的statushot废弃字段。

5、其他属性(不常用)

属性 描述
suffix 数据表后缀(默认为空)
connection 数据库连接(默认读取数据库配置)
query 模型使用的查询类名称
field 模型允许写入的字段列表(数组)
strict 是否严格区分字段大小写(默认为 true
readonly 字段只读
json 设置字段为 JSON 数据
jsonType 设置 JSON 字段的类型
jsonAssoc 设置 JSON 数据返回数组
autoWriteTimestamp 自动写入创建和更新的时间戳字段(默认关闭)
createTime 创建时间戳字段
updateTime 更新时间戳字段
deleteTime 用于定义你的软删除标记字段
defaultSoftDelete 定义软删除字段的默认值

二十四、模型功能

1、获取器

  • 获取器的作用是对模型实例的(原始)数据做出自动处理
  • 命名规则:get + 字段名 + Attr
  • 字段名是数据表字段的驼峰转换
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int',
  14. 'hot' => 'int',
  15. 'status' => 'int'
  16. ];
  17. public function get_data(){
  18. $select = Boke::select();
  19. return $select->toArray();
  20. }
  21. public function getStatusAttr($v){
  22. // echo $v; Status字段的内容
  23. $status = [
  24. 1=>'开启',
  25. 0=>'关闭'
  26. ];
  27. return $status[$v];
  28. }
  29. public function getHotAttr($v){
  30. $hot = [
  31. 1=>'热门',
  32. 0=>'非热门'
  33. ];
  34. return $hot[$v];
  35. }
  36. }

对查询出的数据统一处理

2、修改器

  • 修改器的主要作用是对模型设置的数据对象值进行处理
  • 命名规则: set + 字段名 + Attr
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int',
  14. 'hot' => 'int',
  15. 'status' => 'int'
  16. ];
  17. public function get_data(){
  18. $select = Boke::select();
  19. return $select->toArray();
  20. }
  21. public function getStatusAttr($v){
  22. // echo $v; Status字段的内容
  23. $status = [
  24. 1=>'开启',
  25. 0=>'关闭'
  26. ];
  27. return $status[$v];
  28. }
  29. public function getHotAttr($v){
  30. $hot = [
  31. 1=>'热门',
  32. 0=>'非热门'
  33. ];
  34. return $hot[$v];
  35. }
  36. // 添加的时候
  37. public function add_data($data=[]){
  38. $data = [
  39. 'title' => '新文章',
  40. 'img' => '',
  41. 'content' => '',
  42. 'date' => '2021-06-01',
  43. 'cat' => 2,
  44. 'num' => 0,
  45. 'hot' => 0,
  46. 'status' => 1
  47. ];
  48. $create = Boke::create($data);
  49. return $create;
  50. }
  51. // 修改的时候
  52. public function edit_data(){
  53. $boke = Boke::find(16);
  54. $boke['title'] = '新修改';
  55. $update = $boke->save();
  56. // $update = Boke::where(['bid'=>16])->update(['title'=>'新修改']);
  57. return $update;
  58. }
  59. // 添加和修改的时候,对其标题字段内容统一处理
  60. public function setTitleAttr($v,$all){
  61. // $all 全部参数
  62. // serialize产生一个可存储的值的表示 s:9:"新文章";
  63. return serialize($v);
  64. // 插入和修改标题的时候,将其内容转换为整型
  65. return (int)$v;
  66. // 将标题在前面加上前缀
  67. return '前缀'.$v;
  68. }
  69. }

对插入或修改的数据进行统一格式化处理,检测插入的字段数据是否符合标准等操作。

3、搜索器

  • 搜索器的作用是用于封装字段(或者搜索标识)的查询条件表达式
  • 命名规则: search + 字段名 + Attr
  • 搜索器仅在调用 withSearch 方法的时候触发
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int',
  14. 'hot' => 'int',
  15. 'status' => 'int'
  16. ];
  17. // -------------获取器
  18. public function get_data(){
  19. $select = Boke::select();
  20. return $select->toArray();
  21. }
  22. public function getStatusAttr($v){
  23. // echo $v; Status字段的内容
  24. $status = [
  25. 1=>'开启',
  26. 0=>'关闭'
  27. ];
  28. return $status[$v];
  29. }
  30. public function getHotAttr($v){
  31. $hot = [
  32. 1=>'热门',
  33. 0=>'非热门'
  34. ];
  35. return $hot[$v];
  36. }
  37. // -----------------修改器
  38. // 添加的时候
  39. public function add_data($data=[]){
  40. $data = [
  41. 'title' => '新文章',
  42. 'img' => '',
  43. 'content' => '',
  44. 'date' => '2021-06-01',
  45. 'cat' => 2,
  46. 'num' => 0,
  47. 'hot' => 0,
  48. 'status' => 1
  49. ];
  50. $create = Boke::create($data);
  51. return $create;
  52. }
  53. // 修改的时候
  54. public function edit_data(){
  55. $boke = Boke::find(6);
  56. $boke['title'] = '新修改';
  57. $update = $boke->save();
  58. // $update = Boke::where(['bid'=>16])->update(['title'=>'新修改']);
  59. return $update;
  60. }
  61. // 添加和修改的时候,对其标题字段内容统一处理
  62. public function setTitleAttr($v,$all){
  63. // $all 全部参数
  64. // serialize产生一个可存储的值的表示 s:9:"新文章";
  65. return serialize($v);
  66. // 插入和修改标题的时候,将其内容转换为整型
  67. return (int)$v;
  68. // 将标题在前面加上前缀
  69. return '前缀'.$v;
  70. }
  71. // --------------搜索器
  72. public function s_data(){
  73. $select = Boke::where(['title'=>'新'])->select();
  74. return $select->toArray();
  75. // withSearch方法触发搜索器,将自动查询标题中含有新的所有文章信息
  76. $select = Boke::withSearch(['title'],[
  77. 'title' => '新'
  78. ])->select();
  79. return $select->toArray();
  80. }
  81. public function searchTitleAttr($query,$v){
  82. // $query查询出的对象 $v 查询的字段内容
  83. $query->where('title','like', '%'.$v.'%');
  84. }
  85. }

对查询某个字段时,统一处理该字段查询条件

4、检查数据

  • 如果要判断数据集是否为空,不能直接使用 empty 判断
  • 必须使用数据集对象的 isEmpty 方法判断
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int',
  14. 'hot' => 'int',
  15. 'status' => 'int'
  16. ];
  17. public function get_data(){
  18. $select = Boke::where('title','1')->select();
  19. if(empty($select)){
  20. echo '空';
  21. }else{
  22. echo "不为空";
  23. }
  24. if($select->isEmpty()){
  25. echo 'kong';
  26. }
  27. }
  28. }
  29. s:9:"新文章";
  30. return serialize($v);
  31. // 插入和修改标题的时候,将其内容转换为整型
  32. return (int)$v;
  33. // 将标题在前面加上前缀
  34. return '前缀'.$v;
  35. }
  36. // --------------搜索器
  37. public function s_data(){
  38. $select = Boke::where(['title'=>'新'])->select();
  39. return $select->toArray();
  40. // withSearch方法触发搜索器,将自动查询标题中含有新的所有文章信息
  41. $select = Boke::withSearch(['title'],[
  42. 'title' => '新'
  43. ])->select();
  44. return $select->toArray();
  45. }
  46. public function searchTitleAttr($query,$v){
  47. // $query查询出的对象 $v 查询的字段内容
  48. $query->where('title','like', '%'.$v.'%');
  49. }
  50. }

对查询某个字段时,统一处理该字段查询条件

4、检查数据

  • 如果要判断数据集是否为空,不能直接使用 empty 判断
  • 必须使用数据集对象的 isEmpty 方法判断
  1. namespace app\model;
  2. use think\Model;
  3. class Boke extends Model{
  4. protected $name = 'Boke';
  5. protected $pk = 'bid';
  6. protected $schema = [
  7. 'bid' => 'int',
  8. 'title' => 'string',
  9. 'img' => 'string',
  10. 'content' => 'string',
  11. 'date' => 'date',
  12. 'cat' => 'int',
  13. 'num' => 'int',
  14. 'hot' => 'int',
  15. 'status' => 'int'
  16. ];
  17. public function get_data(){
  18. $select = Boke::where('title','1')->select();
  19. if(empty($select)){
  20. echo '空';
  21. }else{
  22. echo "不为空";
  23. }
  24. if($select->isEmpty()){
  25. echo 'kong';
  26. }
  27. }
  28. }
声明:本文内容转载自脚本之家,由网友自发贡献,版权归原作者所有,如您发现涉嫌抄袭侵权,请联系admin@php.cn 核实处理。
全部评论
文明上网理性发言,请遵守新闻评论服务协议