将行连接到上一个最近的日期行

时间:2013-11-09 14:31:59

标签: php mysql sql

数据库数据:

id | account | date       | random_data
1  | 1       | 01/01/2013 | qw
2  | 2       | 05/01/2013 | er
3  | 2       | 09/01/2013 | ty
4  | 1       | 05/01/2013 | ui
5  | 2       | 11/01/2013 | op
6  | 1       | 12/01/2013 | as

嗨,所以我想说我想要从2013年5月1日开始的记录 - 请注意,第1行的prev_date仍然显示比05/01更早的日期,这意味着仍然需要搜索整个表。

结果数据:

account | cur_date   | random_data | prev_date  | prev_rand_data
1       | 05/01/2013 | ui          | 01/01/2013 | qw
1       | 12/01/2013 | as          | 05/01/2013 | ui
2       | 05/01/2013 | er          | null       | null
2       | 09/01/2013 | ty          | 05/01/2013 | er
2       | 11/01/2013 | op          | 09/01/2013 | ty

所以我不确定什么是我可以使用的最好,最优化的查询。我并不反对PHP解决方案,但不确定会有多好。我考虑过的一些想法:

  1. 在同一张桌子上加入某种形式 - 虽然不知道如何
  2. 对select -

    的子查询

    select date as cur_date , (select max(date) from table where date < cur_date group by account) as prev_date... - 这似乎非常密集

  3. 会话变量 - 在每一行上设置会话变量,这将是下一行的先前数据,例如

    select date as cur_date , @prev_date as prev_date , @prev_date:=date...

  4. 有没有人对这样的问题有任何经验并且有一个很好的解决方案吗?对于我将来可能导致问题的任何想法,是否有任何积极的消极因素?

1 个答案:

答案 0 :(得分:1)

我会使用sql和应用程序代码的组合。由于我不是php程序员,我只会描述用于应用程序部分的逻辑。

首先是查询。

select account, date, random_data
from thetable
where date >= YourDateVariable

union

select account, date, random_data
from thetable join
(select account acc, max(date) maxdate
from thetable
where date <= YourDateVariable
group by account) x on account = acc and date = max(date)
where date <= YourDateVariable

order by account, date

对于应用程序代码,请执行以下操作:

Set a variable called ThisAccount to 0.
Set a row counter variable to 0.
Create an empty 2D array
Start looping through your query results
Put the account value and random data into the first two columns
    of the next available row of the array
Compare the account value to the value of the ThisAccount variable.  
   If they are the same, get the previous date and random data from 
   the previous row in the array.
Set the ThisAccount variable to the current account value.
Increment your row counter variable
End of loop.