2015-03-16 3 views
0

Я расчетаДобавление количества дней Reservation За каждый месяц между Range

  1. количество дней резервирование происходивших в течение каждого месяца (за каждый месяц с момента первой записи)
  2. В общей сложности цена, основанная на общем количестве дней и ставки.

    INSERT INTO `reservations` 
    (`id`, `user_id`, `property_id`,  `actual_check_in`,`actual_check_out`) 
    VALUES 
    (5148, 1, 2, '2014-01-01', '2014-01-10'), 
    (5149, 1, 2, '2014-02-03', '2014-02-10'), 
    (5151, 1, 2, '2014-02-02', '2014-02-15'), 
    (5153, 1, 2, '2014-03-05', '2014-03-10'), 
    (5153, 1, 2, '2014-02-20', '2014-03-30'), 
    
    
    
    
    
    SELECT 
    YEAR(month.d), 
    MONTHNAME(month.d), 
    r.property_id, 
    SUM(
        DATEDIFF(LEAST(actual_check_out, LAST_DAY(month.d)), GREATEST(actual_check_in, month.d)) 
    ) AS days, 
    SUM(days*p.rate), 
    MIN(r.actual_check_in) as firstDate, 
    MAX(r.actual_check_out) as lastDate 
    FROM reservations as r 
    LEFT JOIN property as p on r.property_id=p.id 
    RIGHT JOIN (
          select 
          DATE_FORMAT(m1, '%Y%m%d') as d 
          from 
          (
          select 
          (firstDate - INTERVAL DAYOFMONTH(firstDate)-1 DAY) 
          +INTERVAL m MONTH as m1 
          from 
          (
          select @rownum:[email protected]+1 as m from 
          (select 1 union select 2 union select 3 union select 4) t1, 
          (select 1 union select 2 union select 3 union select 4) t2, 
          (select 1 union select 2 union select 3 union select 4) t3, 
          (select 1 union select 2 union select 3 union select 4) t4, 
          (select @rownum:=-1) t0 
         ) d1 
         ) d2 
          where m1<=lastDate 
          order by m1 
        )  AS month ON 
        actual_check_in <= LAST_DAY(month.d) 
    AND month.d <= actual_check_out 
    GROUP BY user_id, month.d 
    

Неприятность у меня:

  1. получение MySQL принять переменный для firstDate & lastDate в соединенном запросе
  2. Я хочу суммировать ежемесячное количество дней вместе, для оговорок одного и того же пользователя, за тот же месяц. Я пытаюсь включить соответствующие части в подзапрос, чтобы вычислить, что, но возникли проблемы ..

http://sqlfiddle.com/#!9/71e34/1

Я хотел бы иметь результаты, как (если ставка недвижимость 150/день):

DATE  | USER | #Days | Total Rate 
-------------------------------------- 
01/2014 | 1  | 9  | 1350 
01/2014 | 2  | 0  | 0 
02/2014 | 1  | 30 | 4500 
02/2014 | 2  | 0  | 0 
03/2014 | 1  | 35 | 5250 
03/2014 | 2  | 0  | 0 
04/2014 | 1  | 0  | 0 
04/2014 | 2  | 0  | 0 

* # дней может быть больше, чем количество дней в месяц, потому что может быть несколько оговорок существующих в течение этого месяца

UPDATE ---- Это практически решить эту проблему, но я час во избежание неприятностей во второй большой операции выбора, чтобы действительно правильно рассчитать цены. Запрос запрашивает только первый учетный показатель и не выбирает их в соответствии с операцией объединения. Любая помощь?

select 
    r.user_id, 
    DATE_FORMAT(m1, '%b %Y') as date, 
    (SELECT 
     SUM( 
      DATEDIFF(LEAST(actual_check_out, LAST_DAY(m1)), GREATEST(actual_check_in, m1)) 
      ) AS numdays 
     FROM reservations 
     where actual_check_in <= LAST_DAY(m1) 
       AND m1 <= actual_check_out 
       AND user_id=r.user_id 
     GROUP BY m1) as days, 

    (SELECT 
     SUM( 
      DATEDIFF(LEAST(r.actual_check_out, LAST_DAY(m1)), GREATEST(r.actual_check_in, m1)) 
      ) *p.rate 
     FROM reservations as r 
    left join property as p 
    on r.property_id=p.id 
     where actual_check_in <= LAST_DAY(m1) 
       AND m1 <= actual_check_out 
       AND user_id=r.user_id 
     GROUP BY m1) as price 

    from (

    select ('2015-01-01' - INTERVAL DAYOFMONTH('2015-01-01')-1 DAY) +INTERVAL m MONTH as m1 from (
     select @rownum:[email protected]+1 as m from 
      (select 1 union select 2 union select 3 union select 4) t1, 
      (select 1 union select 2 union select 3 union select 4) t2, 
      (select 1 union select 2 union select 3 union select 4) t3, 
      (select 1 union select 2 union select 3 union select 4) t4, 
      (select @rownum:=-1) t0 
     ) d1 
    ) d2 
     cross join reservations as r 
where m1<=CURDATE() group by user_id, m1 order by m1 

http://sqlfiddle.com/#!9/36035/21

+0

Вы не сможете joing по FirstDate и/или lastDate, потому что РЕГИСТРИРУЙТЕСЬ происходит перед вашим MIN() и MAX() получает назначение К тому времени вы пытаетесь JOIN - нет firstDate или lastDate еще – cyadvert

+0

Можете ли вы опубликовать ожидаемый результат, пожалуйста, – cyadvert

+0

@cyadvert Я сделал редактирование с результатами. Благодаря! – Ryan

ответ

0

Все еще не уверены в своем запросе, но ниже запрос может указать вам правильное направление:

SELECT DATE_FORMAT(r.actual_check_in, '%m/%Y') AS mnth, r.user_id, 
DATEDIFF(MAX(r.actual_check_out),MIN(r.actual_check_in)) AS days, 
DATEDIFF(MAX(r.actual_check_out),MIN(r.actual_check_in))*p.rate AS totalRate 
FROM reservations r 
JOIN property p ON r.property_id=p.id 
GROUP BY DATE_FORMAT(r.actual_check_in, '%m/%Y'), r.user_id; 

Это возвращает данные, как показано ниже:

mnth  user_id days totalRate 
------- ------- ------ ----------- 
01/2014  1  9   1350 
02/2014  1  56   8400 
03/2014  1  5   750 
0

http://sqlfiddle.com/#!9/36035/36

 select 
    r.user_id as userId, 
    DATE_FORMAT(m1, '%b %Y') as date, 
    (SELECT 
     SUM( 
      DATEDIFF(LEAST(actual_check_out, LAST_DAY(m1)), GREATEST(actual_check_in, m1)) 
      ) AS numdays 
     FROM reservations 
     where actual_check_in <= LAST_DAY(m1) 
       AND m1 <= actual_check_out 
       AND user_id=userId 
     GROUP BY m1) as days, 

    (SELECT 

      sum(DATEDIFF(LEAST(r.actual_check_out, LAST_DAY(m1)), GREATEST(r.actual_check_in, m1))*p.rate) 

     FROM reservations as r 
     left join property as p 
    on r.property_id=p.id 
     where r.actual_check_in <= LAST_DAY(m1) 
       AND m1 <= r.actual_check_out 
       AND r.user_id=userId 
     GROUP BY m1) as price 

    from (

    select ('2015-01-01' - INTERVAL DAYOFMONTH('2015-01-01')-1 DAY) +INTERVAL m MONTH as m1 from (
     select @rownum:[email protected]+1 as m from 
      (select 1 union select 2 union select 3 union select 4) t1, 
      (select 1 union select 2 union select 3 union select 4) t2, 
      (select 1 union select 2 union select 3 union select 4) t3, 
      (select 1 union select 2 union select 3 union select 4) t4, 
      (select @rownum:=-1) t0 
     ) d1 
    ) d2 
     cross join reservations as r 
where m1<=CURDATE() group by user_id, m1 order by m1 
Смежные вопросы