MySQL算法更新银行交易(最终余额)
Posted
技术标签:
【中文标题】MySQL算法更新银行交易(最终余额)【英文标题】:MySQL algorithm to update bank transaction (final balance) 【发布时间】:2020-12-27 01:47:04 【问题描述】:我还是 mysql 新手,目前正在解决更新银行交易中最终余额的问题。我首先得到了下表。 The given table named as "transaction"
我预计会给出以下结果; The expected result
我设法通过以下 MySQL 代码处理了 credit_balance 列;
UPDATE transaction
SET credit_debit = CASE money_in_or_out
WHEN "OUT" THEN amount*(-1)
ELSE amount*(1)
END;
ALTER TABLE `sql_invoicing`.`transaction`
CHANGE COLUMN `credit_debit` `credit_debit` DECIMAL(9,2) NULL DEFAULT NULL ;
至于余额一栏,我只管写了以下;
UPDATE transaction
SET balance =
(SELECT balance + credit_debit
ORDER BY payment_id DESC
LIMIT 1);
产生以下错误的结果; The returned result
因此,任何人都可以提出任何建议来解决这个问题吗?谢谢!
【问题讨论】:
通常,您会将余额作为帐户表的一部分,而不是作为交易表的一部分。如果您想在每次交易后存储余额,那么我会将其计算为应用程序逻辑的一部分,而不是 sql。基本上是在上一笔交易后取bakance,加上或减去当前交易的值。 @Shadow 嗨,我并不介意账户和交易表(顺便说一句,它只是一个虚拟数据),因为这里的最终目标是让我了解如何编写算法更新银行交易,因为我是 MySQL 新手(刚开始不到 3 周前)。但是,随着我的进步,我会始终牢记这一点。谢谢! 【参考方案1】:您正在描述一个窗口总和。
首先:我不建议存储此类信息,因为维护起来很繁琐。相反,您可以在需要时即时计算它,或者将逻辑放在视图中。
如果你运行的是 MySQL 8.0,你可以只使用窗口函数:
select t.*,
sum(case when money_in_or_out = 'OUT' then - amount else amount end)
over(order by payment_id) as balance
from transaction t
在早期版本中,您可以改用相关子查询:
select t.*,
(
select sum(case when money_in_or_out = 'OUT' then - amount else amount end)
from transaction t1
where t1.payment_id <= t.payment_id
) as balance
from transaction t
注意:人们可能期望一家银行拥有一个以上的客户。您的表应该有一个列来存储该信息,因此可以每个客户计算余额。然后,您将按如下方式修改窗口函数:
sum(case when money_in_or_out = 'OUT' then - amount else amount end)
over(partition by customer_id order by payment_id) as balance
子查询会变成:
(
select sum(case when money_in_or_out = 'OUT' then - amount else amount end)
from transaction t1
where t1.customer_id = t.customer_id and t1.payment_id <= t.payment_id
) as balance
【讨论】:
不,帐户余额通常是您存储的典型例外情况之一,因为随着时间的推移,每次您想检查是否可以进行交易或客户想查看余额。但是,余额通常存储在帐户表中,而不是交易表中。如果您将其存储在交易表中,它将显示交易后的余额 - 这不会改变,因为如果交易完成,那么它就是最终的。 @Shadow:我明白你的意思。但是,您不认为一个答案比多次 cmet 和 downvotes(假设后者是您的)更有帮助吗?以上是关于MySQL算法更新银行交易(最终余额)的主要内容,如果未能解决你的问题,请参考以下文章