tags:

views:

27

answers:

1

Let's say I have a table like this (ordered by id):

id    amount
---   ---
1     10
2     15
3     10
4     30

I want a query which will return rows such that the sum of amount is greater than a given number. So (in a non-existing syntax) SELECT id, amount LIMIT BY running_total(amount) 20 selects first 2 rows, ... LIMIT BY running_total(amount) 60 selects all rows. I can't change the schema to keep the running total precomputed. Can this be done reasonably efficiently? It would be acceptable if the answer works only on SQLite.

+1  A: 

You could use a subquery that sums all rows with a lower id:

select  *
from    YourTable t1
where   20 > coalesce(
        (
        select  sum(amount)
        from    YourTable t2
        where   t2.id < t1.id
        ), 0)

The coalesce is to catch the first row, which has a sum of null.

Andomar
Will this have quadratic behaviour, or are SQL engines smart enough to optimize it?
Alexey Romanov
@Alexey Romanov: Not sure what you mean by quadratic, and if you know a way to see SqlLite's query plan let me know :)
Andomar
The subselect for first row requires looking at 0 rows, for second: 1 row, then 2, 3, etc. If the N-th row is the correct one, we have had to look at 0 + 1 + 2 + ... + (N-1) = N*(N - 1)/2 rows. But it seems clear we only actually need looking at N rows.
Alexey Romanov
@Alexey Romanov: Yeah, in SQL Server you can do it with N rows with a declared variable. Not sure if SQLite supports that. It shouldn't matter unless you're under some weird constraints though (huge dataset AND high performance required)
Andomar