9

SQLite で、ある行のフィールドが前の行のフィールドの値に依存するビューを作成したいと考えています。分析関数を使用してOracleでこれを行うことができましたがLAG、SQLiteでそれを行う方法がわかりません。

たとえば、テーブルが次のようになっているとします。

ITEM        DAY           PRICE
apple       2011-01-07    1.25
orange      2011-01-02    1.00
apple       2011-01-01    1.00
orange      2011-01-03    2.00
apple       2011-01-08    1.00
apple       2011-01-10    1.50

ビューを次のようにしたいと思いますWHERE item = 'apple':

DAY           PRICE    CHANGE
2011-01-01    1.00     (null)
2011-01-07    1.25     0.25
2011-01-08    2.00     0.75
2011-01-10    1.50     -0.50

編集:

私が探しているクエリに相当するものは、Oracleでは次のようになります(これは試していませんが、これは正しいと思います):

SELECT day, price, 
       price - LAG( price, 1 ) OVER ( ORDER BY day ) AS change
  FROM mytable
 WHERE item = 'apple'
4

4 に答える 4

2

これはすべてのトリックを行う必要がありますitem(SQLiteでテスト済み):

SELECT 
    day
    ,price
    ,price - (SELECT t2.price 
              FROM mytable t2 
              WHERE 
                  t2.item = t1.item AND 
                  t2.day < t1.day      
              ORDER BY t2.day DESC
              LIMIT 1
             ) AS change
FROM mytable t1

dayこれは、との組み合わせitemが一意であることを前提としています。そして、それが機能する方法は、指定された 未満のすべての値を取得し、降順ソートdayてから最初の値だけを取得し、関数をシミュレートすることです。LIMITLAG

ビヘイビアの場合は、とにLEADフリップ<するだけです。>DESCASC

于 2017-12-04T10:07:50.670 に答える
2

他のものと同じ考え方ですが、ROWID の代わりにフィールドを使用するだけです。これはまさにあなたが望むことをします:


CREATE TABLE Prices (
    day DATE,
    price FLOAT
);

INSERT INTO Prices(day, price) VALUES(date('now', 'localtime', '+1 day'), 0.5);
INSERT INTO Prices(day, price) VALUES(date('now', 'localtime', '+0 day'), 1);
INSERT INTO Prices(day, price) VALUES(date('now', 'localtime', '-1 day'), 2);
INSERT INTO Prices(day, price) VALUES(date('now', 'localtime', '-2 day'), 7);
INSERT INTO Prices(day, price) VALUES(date('now', 'localtime', '-3 day'), 8);
INSERT INTO Prices(day, price) VALUES(date('now', 'localtime', '-4 day'), 10);

SELECT p1.day, p1.price, p1.price-p2.price 
FROM
    Prices p1, Prices p2,
    (SELECT t2.day AS day1, MAX(t1.day) AS day2 
    FROM Prices t1, Prices t2
    WHERE t1.day < t2.day
    GROUP BY t2.day) AS prev
WHERE p1.day=prev.day1
    AND p2.day=prev.day2

WHERE item='apple'少し追加したい場合は、それを両方のWHERE句に追加します。

于 2012-04-05T07:33:07.720 に答える
0

これを削除しないと仮定すると、次のようになります。


SELECT t2.DAY, t2.price, t2.price-t1.price 
FROM TABLENAME t1, TABLENAME t2 
WHERE t1.rowid=t2.rowid-1

CREATEこれは、ステートメントで指定しなくても、すべての行に独自の行 ID があるため機能します。

削除すると、次のようになります。


SELECT t2.day, t2.price, t2.price-t1.price 
FROM 
     (SELECT l1.day, l1.price, 
          (SELECT COUNT(*) 
          FROM TABLENAME l2 
          WHERE l2.rowid < l1.rowid) AS count
      FROM TABLENAME l1) AS t1,
     (SELECT l1.day, l1.price, 
          (SELECT COUNT(*) 
          FROM TABLENAME l2 
          WHERE l2.rowid < l1.rowid) AS count
      FROM TABLENAME l1) AS t2
WHERE t1.count=t2.count-1

これは、ROWID が常に増加しているという前提で機能します。

于 2012-04-04T00:37:40.853 に答える