你应该检查一下
WHERE imageCount.image_count IS NULL
而不是
WHERE imageCount.image_count=0
因为那些没有任何相关图像的行将显示为
null
在
image_count
并将条件从
$query->andFilterWhere(['imageCount.image_count' => 0]);
$query->andWhere(['is','imageCount.image_count',new \yii\db\Expression('null')]);`
您的查询应该像这样生成
SELECT `item`.* FROM `item`
LEFT JOIN
(
SELECT `item_id`, COUNT(id) as image_count
FROM `image`
GROUP BY `item_id`
) `imageCount`
ON imageCount.item_id = id
WHERE `imageCount`.`image_count` is NULL
使现代化
您在筛选图像计数为0的项目时遇到问题我没有您所拥有的确切模式,但我将在下面说明一个示例,其中有一个类似的场景
Shoots
以及它们在连接表中的相关标记
ShootTag
模型
下面是模式和数据的示例
+----+------------+--------+------------+
| id | name | active | shoot_type |
+----+------------+--------+------------+
| 1 | aslam omer | 1 | modeling |
| 2 | asif | 1 | modeling |
| 3 | saleem | 1 | modeling |
| 4 | sajid | 1 | modeling |
| 5 | tasleem | 1 | modeling |
| 6 | tehseen | 1 | modeling |
| 7 | amjad | 1 | modeling |
| 8 | shaban | 1 | modeling |
| 9 | irfan | 1 | modeling |
+----+------------+--------+------------+
下面是模式和数据的示例
+----------+--------+
| shoot_id | tag_id |
+----------+--------+
| 1 | 1 |
| 1 | 2 |
| 1 | 3 |
| 1 | 4 |
| 2 | 1 |
| 2 | 2 |
| 2 | 3 |
| 3 | 1 |
| 4 | 1 |
| 4 | 4 |
+----------+--------+
现在考虑到上面的表格和数据,我有一个名为的搜索模型
ShootsSearch
我用它来显示所有的快照,我想显示保存在
模型
射击搜索
具有以下搜索方法,该方法可正确用于shoottags模型中针对快照的任何计数。
-
与您的代码不同的是,我正在使用
射击搜索
第一个查询的模型,而不是
射出
使用的模型
Item::find();
应该是哪一个
ItemSearch::find();
而是作为您正在使用的别名
图像计数
-
然后排队
new Expression('if(st.totalTags is NOT NULL,st.totalTags,0) as totalTags')
在主查询中,您需要将空值显示为0,以便在此处使用条件选择。
-
然后你需要检查一下
if ($this->totalTags == '0') {
申请
$query->andWhere(['IS', 'totalTags', new Expression('null')]);
无效的
对于
totalTags
在没有针对任何
Shoot
在其他部分,您将使用
query->andFilterWhere(['=', 'totalTags', $this->totalTags]);
这适用于您希望看到下图的所有三种场景
搜索totalTags计数为4的快照
搜索TotalTags计数为0的快照
您应该在代码中替换以下内容
-
public $totalTags
具有
public $image_count
-
射击标签
具有
Image
.
-
shoot_id
item_id
.
-
具有
ItemSearch
/
self
这是搜索模型,代码已经过测试并运行。
class ShootsSearch extends Shoots
{
/**
* @var mixed
*/
public $totalTags;
/**
* {@inheritdoc}
*/
public function rules()
{
return [
[['id', 'active', 'totalTags'], 'integer'],
[['name', 'shoot_type', 'description', 'totalTags'], 'safe']
];
}
/**
* {@inheritdoc}
*/
public function scenarios()
{
// bypass scenarios() implementation in the parent class
return Model::scenarios();
}
/**
* Creates data provider instance with search query applied
*
* @param array $params
*
* @return ActiveDataProvider
*/
public function search($params)
{
$subQuery = ShootTag::find()->select(
[
new Expression('shoot_id, COUNT(shoot_id) as totalTags')
]
)->groupBy('shoot_id');
$query = ShootsSearch::find()->alias('s')
->select(
[
's.*',
new Expression('if(st.totalTags is NOT NULL,st.totalTags,0) as totalTags')
]
)->leftJoin(['st' => $subQuery], 'st.shoot_id=s.id');
// add conditions that should always apply here
$dataProvider = new ActiveDataProvider(
[
'query' => $query
]
);
$this->load($params);
if (!$this->validate()) {
// uncomment the following line if you do not want to return any records when validation fails
// $query->where('0=1');
return $dataProvider;
}
// grid filtering conditions
$query->andFilterWhere([
'id' => $this->id,
'active' => $this->active
]);
$query->andFilterWhere(['like', 'name', $this->name])
->andFilterWhere(['like', 'shoot_type', $this->shoot_type])
->andFilterWhere(['like', 'description', $this->description]);
if ($this->totalTags == '0') {
$query->andWhere(['IS', 'totalTags', new Expression('null')]);
} else {
$query->andFilterWhere(['=', 'totalTags', $this->totalTags]);
}
return $dataProvider;
}
}