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

 更新时间:2018年10月18日 11:32:08   作者:Rootrl  
这篇文章主要介绍了Laravel关联模型中过滤结果为空的结果集(has和with区别),需要的朋友可以参考下

首先看代码:

$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区别),希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对脚本之家网站的支持!

相关文章

  • 如何让搜索引擎抓取AJAX内容解决方案

    如何让搜索引擎抓取AJAX内容解决方案

    谈到AJAX很多人会联想到JavaScript,直到现在为止各大搜索引擎对如:javascript、ajax、flash代码生成的内容都没办法很好的抓取。但很多站长都很喜欢这些效果,可是偏偏各大搜索引擎不能很好的抓取这些代码所生成的内容,使得很多站长都放弃了这些效果。
    2014-08-08
  • 详解PHP编码转换函数应用技巧

    详解PHP编码转换函数应用技巧

    在PHP语言中mb_convert_encoding是一个PHP编码转换函数,可以帮助我们用来实现对多字节字符串编码的转换。下面将会为大家进行详细介绍。
    2016-10-10
  • php 批量查询搜狗sogou代码分享

    php 批量查询搜狗sogou代码分享

    本文给大家分享的是使用php实现批量查询搜狗的实例代码,非常的简单实用,有需要的小伙伴可以参考下。
    2015-05-05
  • php调用dll的实例操作动画与代码分享

    php调用dll的实例操作动画与代码分享

    这是我录制的一个gif操作动画,图片比较大,如果大家在线看图感觉不流畅的话可以把图片保存到本机再看
    2012-08-08
  • JavaScript实现删除电脑的关机键

    JavaScript实现删除电脑的关机键

    本文给大家分享的是一个恶作剧小程序,使用JavaScript实现删除电脑的关机键,非常有意思,主要是通过ActiveX操作注册表来实现,有需要的小伙伴可以参考下
    2016-07-07
  • PHP环境搭建(php+Apache+mysql)

    PHP环境搭建(php+Apache+mysql)

    这篇文章主要为大家详细介绍了PHP环境搭建,包括php、Apache、mysql环境安装,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2016-11-11
  • php设计模式之正面模式实例分析【星际争霸游戏案例】

    php设计模式之正面模式实例分析【星际争霸游戏案例】

    这篇文章主要介绍了php设计模式之正面模式,结合星际争霸游戏案例形式分析了php正面模式相关原理、使用技巧与操作注意事项,需要的朋友可以参考下
    2020-03-03
  • thinkphp3.x中session方法的用法分析

    thinkphp3.x中session方法的用法分析

    这篇文章主要介绍了thinkphp3.x中session方法,全面分析了thinkPHP中session的初始化、设置、赋值、删除、管理等各种常用操作技巧,需要的朋友可以参考下
    2016-05-05
  • ThinkPHP5.1框架页面跳转及修改跳转页面模版示例

    ThinkPHP5.1框架页面跳转及修改跳转页面模版示例

    这篇文章主要介绍了ThinkPHP5.1框架页面跳转及修改跳转页面模版,结合实例形式分析了thinkPHP5.1框架进行页面跳转及修改跳转模板相关操作技巧,需要的朋友可以参考下
    2019-05-05
  • php设计模式之代理模式分析【星际争霸游戏案例】

    php设计模式之代理模式分析【星际争霸游戏案例】

    这篇文章主要介绍了php设计模式之代理模式,结合星际争霸游戏案例形式分析了PHP设计模式中代理模式的相关原理、使用方法与操作注意事项,需要的朋友可以参考下
    2020-03-03

最新评论