MySQL запрос на подсчет предметов по неделям за текущие 52 недели? - PullRequest
1 голос
/ 24 марта 2012

У меня есть запрос, который я хотел бы изменить, чтобы он подсчитывал мне текущие текущие 52 недели.Этот запрос использует созданную мной таблицу календаря, которая содержит список дат в фиксированном диапазоне.В текущем запросе выбираются максимальные и минимальные даты, а не обязательно последние 52 недели.

Мне интересно, как сохранить текущую таблицу календаря такой, чтобы можно было получать последние 52 недели (т. Е. Изщас год назад).Или есть другой способ сделать запрос независимым от использования таблицы календаря?

Вот запрос:

SELECT calendar.datefield AS date, IFNULL(SUM(purchaseyesno),0) AS item_sales
FROM items_purchased join items on items_purchased.item_id=items.item_id 
RIGHT JOIN calendar ON (DATE(items_purchased.purchase_date) = calendar.datefield)
WHERE (calendar.datefield BETWEEN (SELECT MIN(DATE(purchase_date)) 
FROM items_purchased) AND (SELECT MAX(DATE(purchase_date)) FROM items_purchased)) 
GROUP BY week(date)

мысли?

Ответы [ 2 ]

1 голос
/ 24 марта 2012

Я тоже обычно "симулирую" таблицу на лету, используя переменные @sql, и просто присоединяюсь к ЛЮБОЙ таблице в вашей системе, у которой есть как минимум столько недель, сколько вы хотите. ПРИМЕЧАНИЕ ... при работе с датами я обычно использую только часть даты, которая подразумевает 12:00:00 утра. Кроме того, увеличив дату начала на «7 дней» для «EndOfWeek», теперь вы можете применить условие BETWEEN для записей в течение определенного периода времени ... таких как ваши еженедельные потребности.

Я применил такой пример, чтобы координировать объединение на основе сопоставления дат с еженедельной базой ... Поскольку ваш

select 
      DynamicCalendar.StartOfWeek,
      COALESCE( SUM( IP.PurchaseYesNo ), 0 ) as Item_Sales
   from 
      ( select
              @weekNum := @weekNum +1 as WeekNum,
              @startDate as StartOfWeek,
              @startDate := date_add( @startDate, interval 1 week ) EndOfWeek
           from 
              ( select @weekNum := 0,
                       @startDate := date(date_sub(now(), interval 1 year ))) sqlv,
              AnyTableThatHasAtLeast52Records,
           limit
             52 ) DynamicCalendar
      LEFT JOIN items_purchased IP
         on IP.Purchase_Date bewteen DynamicCalendar.StartOfWeek 
                            AND DynamicCalendar.EndOfWeek
   group by
      DynamicCalendar.StartOfWeek

Это при условии, что ваше значение «BuyYesNo» находится непосредственно в купленной вами таблице. Если это так, нет необходимости присоединяться к таблице ITEMS. Если в таблице предметов есть поле IS, то я бы просто добавил LEFT JOIN для вашей таблицы товаров и получил бы значение из этого.

Однако вы можете использовать контекст dynamicCalendar в МНОГИХ условиях.

1 голос
/ 24 марта 2012

Некоторым людям не нравится этот подход, но я склонен использовать фиктивную таблицу, которая содержит значения от 0 до 1000, а затем использовать производную таблицу для получения необходимых диапазонов -

CREATE TABLE dummy (`num` INT NOT NULL);
INSERT INTO dummy VALUES (0), (1), (2), (3), (4), (5), .... (999), (1000);

Если у вас естьтаблица с автоматически увеличивающимся идентификатором и множеством строк, из которых вы можете сгенерировать ее -

CREATE TABLE `dummy`
SELECT id AS `num` FROM `some_table` WHERE `id` <= 1000;

Просто не забудьте вставить значение 0.

SELECT CURRENT_DATE - INTERVAL num DAY
FROM dummy
WHERE num < 365

Итак, применяя этот подход кПо вашему запросу вы можете сделать что-то вроде этого -

SELECT WEEK(calendar.datefield) AS `week`, IFNULL(SUM(purchaseyesno),0) AS item_sales
FROM items_purchased join items on items_purchased.item_id=items.item_id 
RIGHT JOIN (
    SELECT (CURRENT_DATE - INTERVAL num DAY) AS datefield
    FROM dummy
    WHERE num < 365
) AS calendar ON (DATE(items_purchased.purchase_date) = calendar.datefield)
WHERE calendar.datefield >= (CURRENT_DATE - INTERVAL 1 YEAR)
GROUP BY week(datefield) -- shouldn't this be datefield instead of date?
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...