大霞daxia 2016-11-25 19:06:23 13189次浏览 1条评论 18 9 0

一直以来,我在用with和JoinWith他们两个的时候,我一直搞不清楚他们到底区别是什么,感觉他们相似,所以有时候想起来用哪个就用哪个,但是后来由于我们项目中的一个bug,就是关于他们两者之间的问题,导致数据不准确,然后我就开始看看,他们到底是有什么区别,今天在这里总结了一下,如果哪里有问题,请大神指点一二......

示例1 - 关联表中实际对应的is_del是1, 即删除状态

model代码如下:

public function getProductInfo($id)
{
    $id = intval($id);

    if ($id) {
        $result = self::find()->
            s'. lect('id, product_name, business_id, classification_id')->
            where([self::tableName() . '.id' => $id])->
            with(['classIfication' => function ($query) {
                 $query->select('id , classification_name')->where(['is_del' => 0]);
            }])->
            asArray()->
            one();
    }
    
    return $result;
}

输出的结果如下:

{
  "code": 0,
  "msg": "成功",
  "content": {
    "id": "13",
    "product_name": "大霞测试",
    "business_id": "1",
    "classification_id": "801",
    "classIfication": null
  }
}

sql语句如下:

SELECT `id`, `product_name`, `business_id`, `classification_id`FROM `wx_partner_product` WHERE (`id`=13)

示例2 - 关联表中实际对应的is_del是1, 即删除状态

Model代码如下:

public function getProductInfo($id)
{
    $id = intval($id);

    if ($id) {
        $result = self::find()->
            select(self::tableName() . '.id,'. ' product_name, business_id, classification_id')->
            where([self::tableName() . '.id' => $id])->
            JoinWith(['classIfication' => function ($query) {
                $query->select(PartnerProductClassification::tableName() . '.id' . ' , classification_name')->where([PartnerProductClassification::tableName() . '.is_del' => 0]);
            }])->
            asArray()->
            one();
    }
    
    return $result;
}

打印结果如下:

{
  "code": 0,
  "msg": "成功",
  "content": null
}

Sql语句如下:

SELECT `wx_partner_product`.id, `product_name`, `business_id`, `classification_id` 
FROM `wx_partner_product` 
LEFT JOIN `wx_partner_product_classification` ON `wx_partner_product`.`classification_id`
     = `wx_partner_product_classification`.`id` 
WHERE (`wx_partner_product`.id=13) AND (`wx_partner_product_classification`.is_del=0)

而针对于这两者,官网上是这样说的:

yii\db\ActiveQuery::joinWith() 和 yii\db\ActiveQuery::with() 的区别是 前者连接主模型类和关联模型类的数据表来检索主模型, 而后者只查询和检索主模型类。 检索主模型

由于这个区别,你可以应用只针对一条 JOIN SQL 语句起效的查询条件。 如,通过关联模型的查询条件过滤主模型,如前例, 可以使用关联表的列来挑选主模型数据,

用我自己的语言,总结如下:

注意: 我把关联表,叫做 "副表",

  1. 当你使用关联查询的时候, 你想排除掉副表不满足的条件下, 主表也给排除掉, 那么我们这时候就选 JoinWith
  2. 当你不介意对应的副表是否满足条件时, 只需要把主表显示出来就行了, 那么我们这时就选with
  3. 你观察sql,你会发现, 用with的时候, 没有with对应的sql语句, 而JoinWith对应的sql语句是存在的, 这点可以注意一下
觉得很赞
您需要登录后才可以评论。登录 | 立即注册