使用 PostgreSQL 查询将表数据转换为账本格式

问题描述 投票:0回答:1

我在 PostgreSQL 表中有以下数据:

id 金额 开仓金额 结束金额
1 200 1000 1200
2 -500
3 -200
4 1000

我想将这些数据转换为分类帐格式,根据上一行的

opening_amount
closing_amount
计算
closing_amount
amount

预期结果是:

id 金额 开仓金额 结束金额
1 200 1000 1200
2 -500 1200 700
3 -200 700 500
4 1000 500 1500

我尝试使用

LAG()
函数,但它给出了错误的结果:

id 金额 开仓金额 结束金额
1 200 1000 1200
2 -500 1200 700
3 -200 1000 800
4 1000 1000 2000

这是我尝试过的查询:

WITH ledger_data AS (
    SELECT 
        id,
        amount,
        COALESCE(LAG(closing_amount) OVER (ORDER BY id), 1000) AS opening_amount,  -- Assuming first record's opening balance is 1000
        amount + COALESCE(LAG(closing_amount) OVER (ORDER BY id), 1000) AS closing_amount
    FROM (VALUES
        (1, 200, 1000, 1200),
        (2, -500, NULL, NULL),
        (3, -200, NULL, NULL),
        (4, 1000, NULL, NULL)
    ) AS ledger(id, amount, opening_amount, closing_amount)
)
SELECT 
    id,
    amount,
    opening_amount,
    closing_amount
FROM ledger_data;

问题

LAG()
函数似乎为后续行提供了不正确的结果。我需要以累积方式计算
opening_amount
closing_amount
,其中每一行都取决于前一行的期末余额。

任何人都可以建议我如何修复此查询以正确生成分类帐格式吗?

sql postgresql common-table-expression window-functions lag
1个回答
0
投票
WITH
  ledger_data (
    id, amount, opening_amount, closing_amount
  )
AS
(
  VALUES
    (1,  200, 1000, 1200),
    (2, -500, NULL, NULL),
    (3, -200, NULL, NULL),
    (4, 1000, NULL, NULL)
),
  running_total AS
(
  SELECT 
    id,
    amount,
    SUM(opening_amount)
      OVER (ORDER BY id)
        AS opening_amount,
    SUM(amount)
      OVER (ORDER BY id)
        AS cumulative_amount 
  FROM
      ledger_data
)
SELECT
  id,
  amount,
  opening_amount + cumulative_amount - amount   AS opening_amount,
  opening_amount + cumulative_amount            AS closing_amount
FROM
  running_total
ORDER BY
  id
;
id 金额 开仓金额 结束金额
1 200 1000 1200
2 -500 1200 700
3 -200 700 500
4 1000 500 1500
SELECT 4

小提琴

© www.soinside.com 2019 - 2024. All rights reserved.