Laravel关联模型中过滤结果为空的结果集(has和with区别)


Posted in PHP onOctober 18, 2018

首先看代码:

$userCoupons = UserCoupons::with(['coupon' => function($query) use($groupId){
 return $query->select('id', 'group_id', 'cover', 'group_number', 'group_cover')->where([
   'group_id' => $groupId,
 ]);
}])
// 更多查询省略...

数据结构是三张表用户优惠券表(user_coupons)、优惠券表(coupons),商家表(corps),组优惠券表(group_coupons) (为了方便查看,后两项已去除)

这里我本意想用模型关联查出用户优惠券中属于给定组gourpId的所有数据(如果为空该条数据就不返回)。

但有些结果不是我想要的:

array(20) {
 ["id"]=>
 int(6)
 ["user_id"]=>
 int(1)
 ["corp_id"]=>
 int(1)
 ["coupon_id"]=>
 int(4)
 ["obtain_time"]=>
 int(1539739569)
 ["receive_time"]=>
 int(1539739569)
 ["status"]=>
 int(1)
 ["expires_time"]=>
 int(1540603569)
 ["is_selling"]=>
 int(0)
 ["from_id"]=>
 int(0)
 ["sell_type"]=>
 int(0)
 ["sell_time"]=>
 int(0)
 ["sell_user_id"]=>
 int(0)
 ["is_compose"]=>
 int(0)
 ["group_cover"]=>
 string(0) ""
 ["is_delete"]=>
 int(0)
 ["score"]=>
 int(100)
 ["created_at"]=>
 NULL
 ["updated_at"]=>
 NULL
 ["coupon"]=>
 NULL // 注意返回了coupons为空的数据
}

记录中有的coupon有记录,有的为空。想想也是,with只是用sql的in()实现的所谓预加载。无论怎样主user_coupons的数据都是会列出的。

它会有两条sql查询,第一条查主数据,第二条查关联,这里第二条sql如下:

select `id`, `group_id`, `cover`, `group_number`, `group_cover` from `youquan_coupons` where `youquan_coupons`.`id` in (1, 2, 3, 4, 5, 7, 8, 9, 10, 11, 13, 14) and (`group_id` = 1) and `youquan_coupons`.`deleted_at` is null

如果第二条为空,主记录的关联字段就是NULL。

后来看到了Laravel关联的模型的has()方法,has()是基于存在的关联查询,下面我们用whereHas()(一样作用,只是更高级,方便写条件)

这里我们思想是把判断有没有优惠券数据也放在第一次查询逻辑中,所以才能实现筛选空记录。

加上whereHas()后的代码如下

$userCoupons = UserCoupons::whereHas('coupon', function($query) use($groupId){
  return $query->select('id', 'group_id', 'cover', 'group_number', 'group_cover')->where([
   'group_id' => $groupId,
  ]);
 })->with(['coupon' => function($query) use($groupId){
  return $query->select('id', 'group_id', 'cover', 'group_number', 'group_cover');
 }])-> // ...

看下最终的SQL:

select * from `youquan_user_coupons` where exists (select `id`, `group_id`, `cover`, `group_number`, `group_cover` from `youquan_coupons` where `youquan_user_coupons`.`coupon_id` = `youquan_coupons`.`id` and (`group_ids` = 1) and `youquan_coupons`.`deleted_at` is null) and (`status` = 1 and `user_id` = 1)

这里实际上是用exists()筛选存在的记录。然后走下一步的with()查询,因为此时都筛选一遍了,所以with可以去掉条件。

显然区分这两个的作用很重要,尤其是在列表中,不用特意去筛选为空的数据,而且好做分页。

总结

以上所述是小编给大家介绍的Laravel关联模型中过滤结果为空的结果集(has和with区别),希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

PHP 相关文章推荐
关于页面优化和伪静态
Oct 11 PHP
Codeigniter注册登录代码示例
Jun 12 PHP
Linux下安装oracle客户端并配置php5.3
Oct 12 PHP
PHP使用strtotime计算两个给定日期之间天数的方法
Mar 18 PHP
大家在抢红包,程序员在研究红包算法
Aug 31 PHP
php进行ip地址掩码运算处理的方法
Jul 11 PHP
PHP中FTP相关函数小结
Jul 15 PHP
YII2框架中excel表格导出的方法详解
Jul 21 PHP
php微信公众号开发之二级菜单
Oct 20 PHP
PHP convert_cyr_string()函数讲解
Feb 13 PHP
Yii框架响应组件用法实例分析
Sep 04 PHP
Laravel 集成微信用户登录和绑定的实现
Dec 27 PHP
PHP使用glob方法遍历文件夹下所有文件的实例
Oct 17 #PHP
php 读取文件夹下所有图片、文件的实例
Oct 17 #PHP
PHP使Laravel为JSON REST API返回自定义错误的问题
Oct 16 #PHP
实现PHP中session存储及删除变量
Oct 15 #PHP
PHP实现用session来实现记录用户登陆信息
Oct 15 #PHP
PHP中使用CURL发送get/post请求上传图片批处理功能
Oct 15 #PHP
深入理解 PHP7 中全新的 zval 容器和引用计数机制
Oct 15 #PHP
You might like
Uchome1.2 1.5 代码学习 common.php
2009/04/24 PHP
php_screw 1.5:php加密: 安装与使用详解
2013/06/20 PHP
php获取新浪微博数据API实例
2013/11/12 PHP
zend framework框架中url大小写问题解决方法
2014/08/19 PHP
调试WordPress中定时任务的相关PHP脚本示例
2015/12/10 PHP
tp5(thinkPHP5)框架实现多数据库查询的方法
2019/01/10 PHP
clientX,pageX,offsetX,x,layerX,screenX,offsetLeft区别分析
2010/03/12 Javascript
用javascript模仿ie的自动完成类似自动完成功的表单
2012/12/12 Javascript
jquery统计用户选中的复选框的个数
2014/06/06 Javascript
JavaScript中发布/订阅模式的简单实例
2014/11/05 Javascript
理解JavaScript事件对象
2016/01/25 Javascript
JS简单测试循环运行时间的方法
2016/09/04 Javascript
jQuery动态生成Bootstrap表格
2016/11/01 Javascript
使用nodejs下载风景壁纸
2017/02/05 NodeJs
Vue实现选择城市功能
2017/05/27 Javascript
一个Js文件函数中调用另一个Js文件函数的方法演示
2017/08/14 Javascript
实例讲解v-if和v-show的区别
2019/01/31 Javascript
微信小程序实现图片选择并预览功能
2019/07/25 Javascript
ES6中Symbol、Set和Map用法详解
2019/08/20 Javascript
Vue-router中hash模式与history模式的区别详解
2020/12/15 Vue.js
Python排序搜索基本算法之插入排序实例分析
2017/12/11 Python
示例详解Python3 or Python2 两者之间的差异
2018/08/23 Python
Python使用字典的嵌套功能详解
2019/02/27 Python
django解决订单并发问题【推荐】
2019/07/31 Python
Python中print函数简单使用总结
2019/08/05 Python
Python列表元素常见操作简单示例
2019/10/25 Python
Python函数式编程指南:对生成器全面讲解
2019/11/19 Python
python FTP批量下载/删除/上传实例
2019/12/22 Python
个人简历自荐信
2013/12/05 职场文书
法律专业实习鉴定
2013/12/22 职场文书
《天安门广场》教学反思
2014/04/23 职场文书
校园环保标语
2014/06/13 职场文书
幼儿园母亲节活动总结
2015/02/10 职场文书
2015年小学图书室工作总结
2015/05/18 职场文书
西游降魔篇观后感
2015/06/15 职场文书
oracle连接ODBC sqlserver数据源的详细步骤
2021/07/25 Oracle