sql запрос с INNER JOIN долго отрабатывает

Общие вопросы по использованию второй версии фреймворка. Если не знаете как что-то сделать и это про Yii 2, вам сюда.
Ответить
Аватара пользователя
webplus
Сообщения: 336
Зарегистрирован: 2012.02.24, 22:05

sql запрос с INNER JOIN долго отрабатывает

Сообщение webplus »

Здравствуйте!
написал код, который грузит сервер:

Код: Выделить всё

    public function getDevices($ids_type)
    {

        $query = Device::find()->where([Device::tableName() . '.is_published' => 1, Device::tableName() . '.model' => $this->model]);
        if (!empty($ids_type)) {
            $relation = $this->getModelsType();
            foreach ($ids_type as $key => $id) {
                if(!empty($id)) {
                    $query->joinWith([$relation['relation']['name'] => function($q) use ($key){
                        $q->alias('r' . $key);
                    }]);
                    $query->andWhere(['r' . $key . '.' . $relation['relation']['field'] => $id]);
                }
            }

        }
        $query->groupBy(Device::tableName() . '.id');
        return $query->all();
    }
Вот в debuger sql который он генерирует:

Код: Выделить всё

SELECT `vamp_device`.* FROM `vamp_device` 
INNER JOIN `vamp_device_vamp_model_vamp_321` `r0` ON `vamp_device`.`id` = `r0`.`vamp_device_id` 
INNER JOIN `vamp_device_vamp_model_vamp_321` `r1` ON `vamp_device`.`id` = `r1`.`vamp_device_id` 
INNER JOIN `vamp_device_vamp_model_vamp_321` `r2` ON `vamp_device`.`id` = `r2`.`vamp_device_id` 
INNER JOIN `vamp_device_vamp_model_vamp_321` `r3` ON `vamp_device`.`id` = `r3`.`vamp_device_id` 
INNER JOIN `vamp_device_vamp_model_vamp_321` `r4` ON `vamp_device`.`id` = `r4`.`vamp_device_id`
 INNER JOIN `vamp_device_vamp_model_vamp_321` `r5` ON `vamp_device`.`id` = `r5`.`vamp_device_id`
  INNER JOIN `vamp_device_vamp_model_vamp_321` `r6` ON `vamp_device`.`id` = `r6`.`vamp_device_id` 
  INNER JOIN `vamp_device_vamp_model_vamp_321` `r7` ON `vamp_device`.`id` = `r7`.`vamp_device_id`
   INNER JOIN `vamp_device_vamp_model_vamp_321` `r8` ON `vamp_device`.`id` = `r8`.`vamp_device_id`
    INNER JOIN `vamp_device_vamp_model_vamp_321` `r9` ON `vamp_device`.`id` = `r9`.`vamp_device_id` 
    WHERE ((`vamp_device`.`is_published`=1) AND (`vamp_device`.`model`='Vamp 321')) 
    AND (`r0`.`vamp_model_vamp_321_id`='39') 
    AND (`r1`.`vamp_model_vamp_321_id`='40') 
    AND (`r2`.`vamp_model_vamp_321_id`='41') 
    AND (`r3`.`vamp_model_vamp_321_id`='42') 
    AND (`r4`.`vamp_model_vamp_321_id`='43') 
    AND (`r5`.`vamp_model_vamp_321_id`='44') 
    AND (`r6`.`vamp_model_vamp_321_id`='45') 
    AND (`r7`.`vamp_model_vamp_321_id`='46') 
    AND (`r8`.`vamp_model_vamp_321_id`='47') 
    AND (`r9`.`vamp_model_vamp_321_id`='48') 
    GROUP BY `vamp_device`.`id`
Мне бы проблему решило бы один раз сделать INNER JOIN а потом во where использовать in . т.е. vamp_model_vamp_321_id in (41,42,56)
Но мне нужно чтобы только точные совпадения были, а в in если какого то id нет то он остальные выведет совпадения. А мне надо точные совпадения в vamp_model_vamp_321_id
Сайт по работе в Украине: https://jobis.com.ua/. Сайт по поиску строителей: https://stroyzakaz.com.ua/
Создание сайтов в Киеве: https://webplus.com.ua/ по доступной цене.
Loveorigami
Сообщения: 977
Зарегистрирован: 2014.08.27, 21:54

Re: sql запрос с INNER JOIN долго отрабатывает

Сообщение Loveorigami »

Правильно я понял, вам нужно получить записи, у которых присутствуют все (41,42,56), а не любое из них?
Аватара пользователя
webplus
Сообщения: 336
Зарегистрирован: 2012.02.24, 22:05

Re: sql запрос с INNER JOIN долго отрабатывает

Сообщение webplus »

Loveorigami писал(а): 2019.07.09, 19:58 Правильно я понял, вам нужно получить записи, у которых присутствуют все (41,42,56), а не любое из них?
Да правильно поняли.
Сайт по работе в Украине: https://jobis.com.ua/. Сайт по поиску строителей: https://stroyzakaz.com.ua/
Создание сайтов в Киеве: https://webplus.com.ua/ по доступной цене.
Loveorigami
Сообщения: 977
Зарегистрирован: 2014.08.27, 21:54

Re: sql запрос с INNER JOIN долго отрабатывает

Сообщение Loveorigami »

Ну тогда решение такое
1. Посчитать число выбранных фильтров - (41,42,56) = 3
2. Сгруппировать с подсчетом найденных типов.
3. Искомыми буду те, у которых число найденных строк равно числу фильтров.

Примерно, так

Код: Выделить всё

SELECT `vamp_device`.* , Count(*)  as `total`
FROM `vamp_device` 
INNER JOIN `vamp_device_vamp_model_vamp_321` `r0` ON `vamp_device`.`id` = `r0`.`vamp_device_id`
WHERE `r0`.`vamp_model_vamp_321_id` IN (41,42,56)
GROUP BY `vamp_device`.`id`
HAVING total = 3
Аватара пользователя
webplus
Сообщения: 336
Зарегистрирован: 2012.02.24, 22:05

Re: sql запрос с INNER JOIN долго отрабатывает

Сообщение webplus »

Спасибо! Помогло! Работает!
Сайт по работе в Украине: https://jobis.com.ua/. Сайт по поиску строителей: https://stroyzakaz.com.ua/
Создание сайтов в Киеве: https://webplus.com.ua/ по доступной цене.
Ответить