Warning: Cannot use a scalar value as an array in /home/admin/public_html/forum/include/fm.class.php on line 757

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/include/fm.class.php on line 770

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/topic.php on line 737
Форумы портала PHP.SU :: несколько COUNT и JOIN

 PHP.SU

Программирование на PHP, MySQL и другие веб-технологии
PHP.SU Портал     На главную страницу форума Главная     Помощь Помощь     Поиск Поиск     Поиск Яндекс Поиск Яндекс     Вакансии  Пользователи Пользователи


 Страниц (1): [1]   

> Без описания
Hawkmoth
Отправлено: 09 Февраля, 2014 - 11:58:42
Post Id


Посетитель


Покинул форум
Сообщений всего: 329
Дата рег-ции: Янв. 2012  


Помог: 6 раз(а)




Добрый день, уважаемые форумчане!
Есть две таблицы: одна с товарами (`goods`):
| id | name | price |
другая с перечнем продаж (`sales`):
| id | good | date | status | ,
в которой `good` - это id товара, `date` - дата продажи, `status` - метка отгрузки (1 или 0).

Мне нужно выбрать все товары до определенной цены и подсчитать для каждого товара кол-во продаж и кол-во продаж с завершенной отгрузкой.

Сначала я написал такой запрос:
CODE (SQL):
скопировать код в буфер обмена
  1. SELECT `g`.`name`, `g`.`price`, COUNT (`s`.`id`), COUNT(`t`.`id`) FROM `goods` g JOIN `sales` s ON `g`.`id`=`s`.`goods` JOIN `sales` t ON `s`.`goods`=`t`.`goods` AND `t`.`status`=1 WHERE `g`.`price`<100 ORDER BY `g`.`id`

но COUNT'ы в этом случае перемножаются. Исправил на это:
CODE (SQL):
скопировать код в буфер обмена
  1. SELECT `g`.`name`, `g`.`price`, COUNT (DISTINCT `s`.`id`), COUNT(DISTINCT `t`.`id`) FROM `goods` g JOIN `sales` s ON `g`.`id`=`s`.`goods` JOIN `sales` t ON `s`.`goods`=`t`.`goods` AND `t`.`status`=1 WHERE `g`.`price`<100 ORDER BY `g`.`id`

заметил, что вываливается только одна строчка, а остальные игнорируются. Может, кто-то подскажет рабочее решение?
 
 Top
KingStar
Отправлено: 09 Февраля, 2014 - 12:04:19
Post Id



Участник


Покинул форум
Сообщений всего: 1889
Дата рег-ции: Авг. 2011  
Откуда: Беларусь


Помог: 69 раз(а)




DISTINCT исключает повторяющиеся значение полей, по моему нужно использовать SUM (`s`.`id`) и т.д.

(Отредактировано автором: 09 Февраля, 2014 - 12:06:17)



-----
То что программа работает, не означает что она написана правильно!
 
 Top
Hawkmoth
Отправлено: 09 Февраля, 2014 - 12:09:51
Post Id


Посетитель


Покинул форум
Сообщений всего: 329
Дата рег-ции: Янв. 2012  


Помог: 6 раз(а)




Причем здесь SUM? Зачем мне сумма всех значений id? Проблема в том, что мой криворукий запрос выдает только одну строчку, а остальные товары тупо игнорирует. Возможно, вместо JOIN'а здесь рациональнее использовать подзапрос, но я никак не могу допетрить, как его составить.
(Добавление)
Вот такой запрос вроде работает:
CODE (SQL):
скопировать код в буфер обмена
  1. SELECT `g`.`id`,`g`.`name`,`g`.`price`,COUNT(DISTINCT `s`.`id`),COUNT(DISTINCT `t`.`id`) FROM `goods` g LEFT JOIN `sales` s ON `g`.`id`=`s`.`good` LEFT JOIN `sales` t ON `s`.`good`=`t`.`good` AND `t`.`status`=1 WHERE `g`.`price`<100 GROUP BY `g`.`id` ORDER BY `g`.`id`

но я не уверен, что правильно.
Может, у кого-то есть более изящное решение?
(Добавление)
Сделал подзапросами
CODE (SQL):
скопировать код в буфер обмена
  1. SELECT `g`.`id`,`g`.`name`,`g`.`price`,(SELECT COUNT(`id`) FROM `sales` WHERE `good`=`g`.`id`) AS `all_sales`, (SELECT COUNT(`id`) FROM `sales` WHERE `good`=`g`.`id` AND `status`=1) AS `complete_sales` WHERE `g`.`price`<100 ORDER BY `g`.`id`
 
 Top
Champion Супермодератор
Отправлено: 09 Февраля, 2014 - 16:05:55
Post Id



Активный участник


Покинул форум
Сообщений всего: 4350
Дата рег-ции: Авг. 2008  
Откуда: Москва


Помог: 57 раз(а)




Hawkmoth, group by же
KingStar пишет:
моему нужно использовать SUM (`s`.`id`)
Мне чуть доктор не понадобился. Не говорите так больше
 
 Top
KingStar
Отправлено: 09 Февраля, 2014 - 18:04:51
Post Id



Участник


Покинул форум
Сообщений всего: 1889
Дата рег-ции: Авг. 2011  
Откуда: Беларусь


Помог: 69 раз(а)




Champion, не понял Хм
(Добавление)
в плане логики - ну да, затупил Смущение больше не буду Подмигивание


-----
То что программа работает, не означает что она написана правильно!
 
 Top
tuareg
Отправлено: 09 Февраля, 2014 - 18:37:03
Post Id


Участник


Покинул форум
Сообщений всего: 1234
Дата рег-ции: Июнь 2010  


Помог: 69 раз(а)




Как-то так.
CODE (SQL):
скопировать код в буфер обмена
  1.  
  2. SELECT `g`.`name`, `g`.`price`,
  3. COUNT (`s`.`id`)  AS sales,
  4. SUM(IF(`s`.`status`=1 , 1, 0)) AS shipped
  5. FROM `goods` g
  6. INNER JOIN `sales` s ON `g`.`id`=`s`.`goods`
  7. WHERE `g`.`price`<100 GROUP BY `g`.id ORDER BY `g`.`id`
  8.  

Поиграйтесь, второй join `sales` тут не нужен 100%

(Отредактировано автором: 09 Февраля, 2014 - 19:15:09)

 
 Top
Страниц (1): [1]
Сейчас эту тему просматривают: 0 (гостей: 0, зарегистрированных: 0)
« Работа с СУБД »


Все гости форума могут просматривать этот раздел.
Только зарегистрированные пользователи могут создавать новые темы в этом разделе.
Только зарегистрированные пользователи могут отвечать на сообщения в этом разделе.
 



Powered by PHP  Powered By MySQL  Powered by Nginx  Valid CSS  RSS

 
Powered by ExBB FM 1.0 RC1. InvisionExBB