【三】Tp常见的辅助方法

原生SQL语句里除了目前所使用的基本操作增删改查,还有类似于group、where、order、limit等这样的字句。

ThinkPHP封装了相应的子句方法:封装的方法都在父类模型Model.class.php

where      表示限制查询的条件

limit         限制输出的条数

filed        限制输出的字段,也就是select id,name,age等类似语句

注意:下面两个方法在父类模型中不存在,方法不存在会走魔术方法__call(),利用__call()方法实现一些特殊的Model方法,而group和order在链操作方法列表,经过__cal()方法调用。实现相应方法。除此外还有alias(别名),having(限制查询条件),distinct(去重),filter(过滤)。

order      字段排序

group      按照指定字段进行分组查询

下面依次介绍:

(1)where

作用:限制查询条件

原生sql语句:select 字段 from 表名 where 条件;

ThinkPHP中封装的where方法:

$model -> where(条件表达式);//ThinkPHP条件表达式支持字符串形式('id=1'),也支持数组形式(array(id=>'1')),推荐使用字符串形式
$model -> CURD操作;

案例:使用where查询表中数据('id>20')

原生SQL语句:

select * from sp_dept where id>20;

ThinkPHP的where方法:

public function test(){
//实例化模型
$model = M('dept');
//where查询
$model -> where('id>20 and id<22');
//验证 dump($model);die;
$data = $model -> select();//这里可以不添加参数,上面输出$model验证下
dump($data);
}

验证$model输出如下:

["options":protected] => array(1) {
["where"] => array(1) {
["_string"] => string(5) "id>20 id<22"
}
}

底层父类模型:

// 分析表达式
$options = $this->_parseOptions($options);

跟踪信息的sql:SELECT * FROM `sp_dept` WHERE ( id>20 and id<22) [ RunTime:0.0000s ]

回顾:在MySQL里除了where外,having也可以限制查询

面试题:where和having都可以限制查询条件,区别是什么?

where表示限制查询条件,要求查询字段必须是数据表中存在的字段;而having要求结果集(查询出的数据结果)中存在的字段

(2)limit方法

限制输出的条数(典型应用,数据的分页)

原生SQL语句:

select 字段 from 表名 where 条件 limit 限制的条数;

ThinkPHP中封装的limit方法:

①$model -> limit(n); //n为大于0的数字,表示输出表中的前n行
②$model -> limit(起始位置,偏移量); //表示从起始位置开始,往后查询指定长度的记录数。实际使用中还支持$model -> limit('起始位置,偏移量')的写法

案例:使用limit实现查询表中的数据限制

①查询前n条

public function test(){
//实例化模型
$model = M('dept');
//限制记录
$model -> limit(2);//查询前2条
$data = $model -> select();
dump($data);
}

跟踪信息的SQL语句:SELECT * FROM `sp_dept` LIMIT 2 [ RunTime:0.0000s ]

②查询带偏移量的形式

public function test(){
//实例化模型
$model = M('dept');
//限制记录
$model -> limit(2,2);//查询从第三条开始的两条记录
$data = $model -> select();
dump($data);
}

跟踪信息SQL语句:SELECT * FROM `sp_dept` LIMIT 2,1 [ RunTime:0.0000s ]

注意:limit从0开始,所以如果想从第3条开始,传入2即可

(3)field方法

作用:限制输出的结果集字段

类似于:原生SQL的select id,name,age

语法:

$model -> field('字段1,字段2...字段n[as 别名,支持别名]');   //参数就是select之后from之前的一串字符串

案例:限制结果集输出,只显示id,name信息

原生sql:

select id,name from sp_dept;

ThinkPHP封装的field方法:

public function test(){
//实例化模型
$model = M('dept');
//条件限制
$model -> where('id>20 and id<22');
//结果集记录限制
$model -> field('id,name');
//执行查询
$data = $model -> select();
dump($data);
}

跟踪信息SQL语句:SELECT `id`,`name` FROM `sp_dept` WHERE ( id>20 and id<22 ) [ RunTime:0.0010s ]

(4)order方法

作用:按照指定的字段进行指定规则排序

原生SQL语法里:

order by 字段 排序规则(升序ase/降序desc)

ThinkPHP封装的语法:

$model -> order('字段名 排序规则');

案例:使用order方法,查询部门表中数据,并且按照id进行降序排列

原生SQL语句

select * from sp_dept order by id desc;

ThinkPHP方法

public function test(){
//实例化模型
$model = M('dept');
$model -> where('id>20');
//按照id降序排序
$model -> order('id desc');
//查询
$data = $model -> select();
dump($data);
}

跟踪信息SQL语句:SELECT * FROM `sp_dept` WHERE ( id>20 ) ORDER BY id desc [ RunTime:0.0000s ]

(5)group方法

作用:用于分组查询

ThinkPHP封装的group方法

$model -> group('字段名');//按照字段名进行分组,相当于group by 字段名

案例:查询部门表,查询出部门名称和出现的次数

原生SQL

select name,count(*) as count from sp_dept group by name;

ThinkPHP的group辅助方法

因为上面使用了限制字段和分组查询,所以只靠group方法,无法实现。需要配合field方法配合

public function test(){
//实例化模型
$model = M('dept');
//指定字段和分组
$model -> group('name');
$model -> field('name,count(*) as count');
// dump($model);die;
//查询
$data = $model -> select();
dump($data);
}

输出结果:

array(3) {
[0] => array(2) {
["name"] => string(4) "tony"
["count"] => string(1) "1"
}
[1] => array(2) {
["name"] => string(9) "技术部"
["count"] => string(1) "3"
}
[2] => array(2) {
["name"] => string(9) "新天剑"
["count"] => string(1) "2"
}
}

跟踪信息SQL语句:SELECT `name`,count(*) as count FROM `sp_dept` GROUP BY name [ RunTime:0.0010s ]

【四】连贯操作

(1)简介

将辅助方法全部写在一行上的写法为连贯操作

语法:$model -> where() -> limit() ->order() -> field() -> select{}

中间标红的即为辅助方法

辅助方法顺序:在连贯操作里,没有顺序要求。只要模型在头部,CURD方法在尾部即可

案例:连贯操作改写

public function test(){
//实例化模型
$model = M('dept');
//连贯操作查询
$data = $model -> field('name,count(*) as count') ->group('name')-> select();
dump($data);
}

问题:为什么辅助方法可以写在一行上?

查看分析父类模型,例如field()返回的都是对象本身$model

/**
* 指定查询字段 支持字段排除
*/
public function field($field,$except=false){
if(true === $field) {// 获取全部字段
$fields = $this->getDbFields();
$field = $fields?:'*';
}elseif($except) {// 字段排除
if(is_string($field)) {
$field = explode(',',$field);
}
$fields = $this->getDbFields();
$field = $fields?array_diff($fields,$field):$field;
}
$this->options['field'] = $field;
return $this;
}

原因就是每一个辅助方法最后的返回值都是$this,而$this是指当前模型类。由模型类去调用后续的辅助方法,这个是行得通的。

之所以将select()等具体的CURD操作方法放到最后,是因为它返回的是数组结果集 ,结果集无法调用辅助方法。所以CURD操作必须放到最后

注意:开发过程里都会遵循使用连贯操作的形式来替代单个辅助方法的写法,优点可读性高

【五】Tp中的统计查询

ThinkPHP中系统封装了以下几个查询方法的使用,方便后期统计的使用。以下几个查询方法在父类模型中不存在,都是由魔术方法__call()生成的

包含count(),max(),min(),avg(),sum()

(1)count()    查询表中总的记录数(有where时表示查询指定条件的记录数)

(2)max()     查询某个字段的最大值

(3)min()      查询某个字段的最小值

(4)avg()      查询某个字段的平均值

(5)sum()     查询某个字段的总和

下面依次介绍

(1)count()

语法:$model -> [where() ->]count;      where可选

public function test(){
//实例化模型
$model = M('dept');
$count = $model->count();
dump($count);//返回字符形式的记录总数
}

跟踪信息的sql语句:SELECT COUNT(*) AS tp_count FROM `sp_dept` LIMIT 1 [ RunTime:0.0010s ]

(2)max()

语法:$model->max('字段名');查询指定字段名的最大值

注意:开发中常用来查找最后一个会员注册id

案例:

public function test(){
//实例化模型
$model = M('dept');
$count = $model->max('id');
dump($count);//返回字符形式
}

跟踪信息SQL:SELECT MAX(id) AS tp_max FROM `sp_dept` LIMIT 1 [ RunTime:0.0010s ]

(3)min()

语法:$model->min('字段名');   指定字段的最小值

注意:实际开发里常用来查询最早注册的会员id

案例:

public function test(){
//实例化模型
$model = M('dept');
$count = $model->min('id');
dump($count);//返回字符形式字符值
}

跟踪信息SQL值:SELECT MIN(id) AS tp_min FROM `sp_dept` LIMIT 1 [ RunTime:0.0000s ]

(4)avg()

语法:$model -> avg('字段名');  查询字段平均值

public function test(){
//实例化模型
$model = M('dept');
$count = $model->avg('id');
dump($count);//返回字符形式,并保留4位小数
}

跟踪信息SQL:SELECT AVG(id) AS tp_avg FROM `sp_dept` LIMIT 1 [ RunTime:0.0000s ]

(5)sum

语法:$model -> sum('字段名');  查询某个字段的总和

public function test(){
//实例化模型
$model = M('dept');
$count = $model->sum('id');
dump($count);//返回字符形式字段总和
}

跟踪信息SQL:SELECT SUM(id) AS tp_sum FROM `sp_dept` LIMIT 1 [ RunTime:0.0000s ]

【六】拓展:fetchSql

之前介绍了sql调试的方法getLastSql(别名_sql),但是该方法要求最后一条成功执行的sql,如果拿着个方法来调试sql,只能调试逻辑错误,不能调试语法错误。

所以出现了建立在连贯操作上的fetchSql方法

语法:$model ->where() -> limit() -> order() -> fetchSql(true) -> CURD操作

位置:fetchSql()可以看做是一个辅助方法,所以可以放到模型后,CURD操作之前任意位置。

例如:$model->where()->limit()->order()->fetchSql(true)->CURD操作

版本要求:必须是3.2.3版本之后才可以用

与getLastSql区别:返回值不同,且不会执行sql语句,只会返回sql语句。而getLastSql会返回并执行sql语句

public function test(){
//实例化模型
$model = M('dept');
$count = $model->field('name,count(*) as count') ->group('name')->fetchSql(true)->select();
dump($count);//返回sql语句SELECT `name`,count(*) as count FROM `sp_dept` GROUP BY name
}

跟踪信息SQL没有显示,说明没有被执行,只是被返回(因为没有被执行,所以即使语法错误也不会执行,都将会返回sql语句)。

ThinkPHP---辅助方法的更多相关文章

  1. thinkphp辅助方法,数据库操作

  2. MVC学习系列4--@helper辅助方法和用户自定义HTML方法

    在HTML Helper,帮助类的帮助下,我们可以动态的创建HTML控件.HTML帮助类是在视图中,用来呈现HTML内容的.HTML帮助类是一个方法,它返回的是string类型的值. HTML帮助类, ...

  3. 《ASP.NET MVC高级编程(4版)》读书笔记(5)表单和HTML辅助方法

    5.1 表单使用 5.1.1 action 和 method 特性 <form action="/Home/Index">     <input name=&qu ...

  4. MVC辅助方法

    我相信很多人虽然经常用mvc去做一些东西,但是可能很少使用mvcHtml辅助方法 首先我们要创建一个mvc项目 二创建一个HtmlHelper文件夹 三编写文件 四调用辅助方法 调用辅助方法 和使用其 ...

  5. ASP.NET 中HTML和Form辅助方法

    Form辅助方法 Form最重要的属性就是action和method,action指明form中的数据被提交到哪里,method指明用什么方法,默认为GET,下面是一个简单的例子: <form ...

  6. MVC之路随记3--Html辅助方法

    概述:MVC中使用@Html.MethodName 来做很多Html的事情,简化了开发工程量,使用方便,并且易于理解 详细方法: 1.表单 <form action="/Home/Se ...

  7. 表单和 HTML 辅助方法– ASP.NET MVC 4 系列

           这里有一个疑问,诸如在文本编辑器中输入 HTML 元素如此简单的任务,也需要任何帮助吗?的确,输入标签名称是很容易的事,但是确保 HTML 页面链接中的 URL 指向正确的位置.表单元素 ...

  8. MVC中使用内建的HTML辅助方法产生表单元素提交表单与button按钮事件的陷阱

    网站模板页有个登陆的退出按钮,当点击时跳转到登陆页面. <button onclick="logout()" >退出</button> $("#l ...

  9. MVC4.0 扩展辅助方法

    新年第一天上班,写个博客开头吧! 在MVC中,辅助类是很常见的,比如说,Html.TextBox().Html.DropDownListFor()等,这些都是微软帮我们封装好的,可以直接调用的,它们解 ...

  10. Linux共享库 socket辅助方法

    //sockhelp.h#ifndef _vx #define _vx #ifdef __cplusplus extern "C" { #endif /** * readn - 读 ...

随机推荐

  1. 第二十七篇:Windows驱动中的PCI, DMA, ISR, DPC, ScatterGater, MapRegsiter, CommonBuffer, ConfigSpace

    近期有些人问我PCI设备驱动的问题, 和他们交流过后, 我建议他们先看一看<<The Windows NT Device Driver Book>>这本书, 个人感觉, 这本书 ...

  2. tomcat的HTTPS

    完美配置Tomcat的HTTPS 博客分类: Tomcat HTTPS   Tomcat配置HTTPS的文章到处都有,过程也比较简单,随后文中会转一段过来. 但对于启用APR情况下报异常“java.l ...

  3. js坑爹笔试题目汇总(持续更新中)

    把你的面试官问倒,你就是一个合格的面试者了,以下总结一些易错的js笔试题目,会持续更新中.欢迎关注 1,考察this var length = 10 function fn(){ alert(this ...

  4. 跟踪oracle中sql语句运行过程及相关知识拓展

    select * from v$sqlarea; select * from v$sqlarea where first_load_time>'2010-11-27/09:30:00'; 这种方 ...

  5. 代理ip 测试

    Line #1218 : 101.232.208.245 - - [16/Jan/2018:02:47:34 +0800] "GET /?xltestdesfs HTTP/1.1" ...

  6. linux常见基础问题

    1,32位与64位的区别,怎么查看系统版本? 32位相比于64位处理速度更慢一些,64位同样也比32位更占内存.用户体验上没有区别:用uname  -a 查看系统版本信息 2,swap分区的作用是什么 ...

  7. 国产手机没有google services 和google play崩溃,判断google services是否存在

    public static boolean isGooglePlayServiceAvailable (Context context) { int status = GooglePlayServic ...

  8. is not mapped [from错误

    我出现的错误是:org.hibernate.hql.ast.QuerySyntaxException: loginuser is not mapped [from loginuser] 配置文件如下: ...

  9. bzoj 1622: [Usaco2008 Open]Word Power 名字的能量【模拟】

    模拟即可,注意包含可以是不连续的 方便起见读入的时候全转成小写 #include<iostream> #include<cstdio> using namespace std; ...

  10. android_app c++框架

    找遍了全网,没有一个完整的可用的框架.ndk自带的android_native_app_glue确实不太好用,闭关几天,写出了一个框架.完全的消息队列调用,目前测试的主体框架是没有什么问题了,程序入口 ...