Mysql
 sql >> база данни >  >> RDS >> Mysql

Попълване на празнини в датите, върнати от базата данни - възможно ли е чисто SQL решение?

Да, по-добре е да създадете таблица с числа (единична колона N), която не съдържа нищо освен числата от 0 до 999. Може да се използва за много неща, не на последно място за заявка като по-долу:

SELECT COUNT(t.click_date) as clicks,
    DATE_FORMAT(adddate($start_date, interval N day), '%d %M %Y') as point 
FROM Numbers
LEFT JOIN tracking t
    ON t.click_date >= adddate($start_date, interval N day)
    and t.click_date < adddate($start_date, interval (N+1) day)
WHERE N between 0 and datediff($start_date, $end_date)
GROUP BY N

Използвате грешен формат. Това е ГОРЕНА буква W не е по-ниска за ден от седмицата, така че '%W %M %Y' или „%d %M %Y“ за ден от месеца.http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html#function_date-format

Използвате GROUP BY DAY(FROM_UNIXTIME(click_date)) бележка "ден" не е делничен ден, но показвате (или се опитвате) "%W" (делен ден) - изберете едно, не ги смесвайте.

РЕДАКТИРАНЕ: Ако предпочитате да не материализирате (създайте като реална таблица) таблица с последователност от числа, можете да създадете такава в движение. Няма да е красиво.

Забележка:N1, N2 и N3 по-долу се комбинират, за да дадат възможен диапазон от 0-999

SELECT COUNT(t.click_date) as clicks,
    DATE_FORMAT(adddate($start_date, interval N day), '%d %M %Y') as point 
FROM (
    select N1 * 100 + N2 * 10 + N3 as N
    from (
    select 0 N1 union all select 1 union all select 2 union all
    select 3 union all select 4 union all select 5 union all
    select 6 union all select 7 union all
    select 8 union all select 9) N1
    cross join (
    select 0 N2 union all select 1 union all select 2 union all
    select 3 union all select 4 union all select 5 union all
    select 6 union all select 7 union all
    select 8 union all select 9) N2
    cross join (
    select 0 N3 union all select 1 union all select 2 union all
    select 3 union all select 4 union all select 5 union all
    select 6 union all select 7 union all
    select 8 union all select 9) N3
    ) Numbers
LEFT JOIN tracking t
    ON t.click_date >= adddate($start_date, interval N day)
    and t.click_date < adddate($start_date, interval (N+1) day)
WHERE N between 0 and datediff($start_date, $end_date)
GROUP BY N

РЕДАКТИРАНЕ №2: Права таблица с дати

Поставете това в нов прозорец в phpMyAdmin или го стартирайте като пакет. Той създава таблица с име Дати, с всяка отделна дата от ден 1900-01-01 (или промяна в скрипта) на 2300-01-01 (или промяна).

DROP PROCEDURE IF EXISTS FillDateTable;

delimiter //
CREATE PROCEDURE FillDateTable()
    LANGUAGE SQL
    NOT DETERMINISTIC
    CONTAINS SQL
    SQL SECURITY DEFINER
    COMMENT ''
BEGIN
  drop table if exists datetable;
  create table datetable (thedate datetime primary key, isweekday smallint);

  SET @x := date('1900-01-01');
  REPEAT 
    insert into datetable (thedate, isweekday) SELECT @x, case when dayofweek(@x) in (1,7) then 0 else 1 end;
    SET @x := date_add(@x, interval 1 day);
    UNTIL @x > date('2300-01-01') END REPEAT;
END//
delimiter ;

CALL FillDateTable;

С такава таблица с помощни програми вашата заявка може да бъде просто

SELECT COUNT(t.click_date) as clicks,
    DATE_FORMAT(thedate, '%d %M %Y') as point 
FROM Dates
LEFT JOIN tracking t
    ON t.click_date >= thedate
    and t.click_date < adddate(thedate, interval 1 day)
WHERE thedate between $start_date and $end_date
GROUP BY thedate


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Проблеми с часовата зона с PHP и MySQL

  2. Как да актуализирате колона с нулева стойност

  3. Как да се свържа с MySQL с помощта на UTF8 в рамките на perl скрипт?

  4. Как да премахнете интервали от низ в MySQL

  5. SQL заявка:Изтриване на всички записи от таблицата с изключение на последния N?