我知道有很多关于这个问题的话题,但没有一个真正帮助我解决了我的问题。在数据库方面我仍然是一个新的东西,我遇到了这个问题。
我有一个名为tests的表,其中包含两列:id和date。
我想计算几个值之间的平均天数差异。
说select date from tests where id=1
,它将为我提供日期列表。我想计算那些日子之间的平均差异。
表“测试”
1|2018-03-13
1|2018-03-01
2|2018-03-13
2|2018-03-01
3|2018-03-13
3|2018-03-01
1|2018-03-17
2|2018-03-17
3|2018-03-17
从id = 1
的测试中选择日期2018-03-13
2018-03-01
2018-03-17
现在我想计算这三个日期之间的平均天数差异。 可以真的使用一些帮助,谢谢!
编辑: 很抱歉不清楚,我会澄清我的问题。 所以学生们在01/03进行了测试,然后是在13/03,然后在17/03。我想要计算的是测试到测试之间的平均天数差异,所以: 第一到第二之间的差异是12天。第二到第三的差异是4天。 由于我们有两个缺口,因此12 + 6除以2,即8 8。
答案 0 :(得分:0)
- 我希望计算这三个日期之间的平均天数差异。*
平均差异是指"取所有日期之差的绝对值的平均值"。那是12 + 16 + 4 / 3
或10.6667。
We need all combinations of dates。为此,我们需要一个没有重复的自连接。通过选择字段并将on
与<
或>
一起使用来实现这一目标。
select t1.date, t2.date
from tests as t1
join tests as t2 on t1.id = t2.id and t1.date < t2.date
where t1.id = 1;
2018-03-01|2018-03-13
2018-03-01|2018-03-17
2018-03-13|2018-03-17
既然我们拥有所有组合,我们就能发挥作用。但不是简单地减去日期,SQLite并不支持。首先,将它们转换为Julian Days。
sqlite> select julianday(t1.date), julianday(t2.date) from tests as t1 join tests as t2 on t1.id = t2.id and t1.date < t2.date where t1.id = 1;
2458178.5|2458190.5
2458178.5|2458194.5
2458190.5|2458194.5
既然我们有数字,我们可以取差值的绝对值并做平均值。
select avg(abs(julianday(t1.date) - julianday(t2.date)))
from tests as t1
join tests as t2 on t1.id = t2.id and t1.date < t2.date
where t1.id = 1;
更新
我想要计算的是测试与测试之间的平均天数差异,因此:第一到第二之间的差异是12天。第二到第三的差异是4天。然后(12 + 4)/ 2 = 8应该是结果。
对于问题的这种扭曲,你想要将每一行与下一行进行比较。你想要一个像这样的表:
2018-03-01|2018-03-13
2018-03-13|2018-03-17
其他数据库具有window
或lag
等功能来完成此任务。 SQLite没有这个。同样,我们将使用自联接,但我们必须每行执行一次。这是correlated subquery。
select t1.date as date, (
select t2.date
from tests t2
where t1.id = t2.id and t2.date > t1.date
order by t2.date
limit 1
) as next
from tests t1
where id = 1
and next is not null
subquery-as-column查找每行的下一个日期。
这有点笨拙,所以让我们把它变成一个视图。然后我们可以将它用作表格。只需取出where id = 1
,这样就非常有用。
create view test_and_next as
select t1.id, t1.date as date, (
select t2.date
from tests t2
where t1.id = t2.id and t2.date > t1.date
order by t2.date
limit 1
) as next
from tests t1
where next is not null
现在,我们可以将test_and_next
视为包含id
,date
和next
列的表格。然后它和以前一样:把它们变成朱利安日,减去并取平均值。
select avg(julianday(next) - julianday(date))
from test_and_next
where id = 1;
请注意,当您有两行具有相同日期时,这将会横向移动:SQL无法知道哪个是&#34; next&#34;一。例如,如果在&#34; 2018-03-13&#34;他们都会选择&#34; 2018-03-17&#34;作为&#34; next&#34;之一。
2018-03-01|2018-03-13
2018-03-13|2018-03-17
2018-03-13|2018-03-17
我不确定如何解决这个问题。