为了账号安全,请及时绑定邮箱和手机立即绑定

多线程:多个线程与同一个表交互

多线程:多个线程与同一个表交互

摇曳的蔷薇 2023-03-02 10:27:24
面试题比如说,我们有一张 Employee 表中有 200 万条记录的表,我们需要削减每个员工 10% 的工资(需要做一些处理),然后将其存回集合。你怎么能有效地做到这一点。我问他我们可以使用执行器框架来创建多个线程,这些线程可以从表中获取值,然后我们可以处理并将其保存到列表中。然后他问我你将如何检查记录是否已被处理,我对此一无所知(怎么做)。即使我不确定我是否擅长我的方法。请帮忙。
查看完整描述

3 回答

?
饮歌长啸

TA贡献1951条经验 获得超3个赞

给出问题的最佳方法是使用纯 SQL,例如:


update employees set

salary = salary * .9

很难想象需要对 SQL 无法处理的员工数据执行某些操作。


如果由于某种不良设计的怪癖,您确实需要对 SQL 绝对无法执行的员工类型数据执行某些操作,那么您将打开一个指向行集的游标并遍历它,同步进行更新,这样您只需执行一次传递数据。


在伪代码中:


cursor = forUpdate ("select for update * from employees")

while (cursor.next()) {

    cursor.salary = cursor.salary * .9

}

这是最简单且执行速度可能最快的方法。


—-


关于日志记录

它只有 2M 行,这是一个“小”数量,因此大多数 DB 可以在单个事务中处理它。但是,如果没有,请添加一个 where 子句,例如,where id between <start> and <end>如果使用 shell 脚本方法,则将过程分块到可记录的数量的查询中。


如果使用代码方法,大多数数据库允许您在保持游标打开的情况下提交,因此只需每 10K 行左右提交一次。


关于锁定

与日志记录类似的方面。在事务期间,此类查询中的所有行都被锁定。鉴于跑步需要那么长时间,请选择一个安静的时间跑步。如果这真的很重要,请分块,但要意识到锁定是不可避免的。


查看完整回答
反对 回复 2023-03-02
?
天涯尽头无女友

TA贡献1831条经验 获得超9个赞

您可以做的一件事是使用生产者/消费者类型模型,其中您有一个线程工作以向其他线程提供要更新的记录。这样您就不必担心重复处理。



查看完整回答
反对 回复 2023-03-02
?
FFIVE

TA贡献1797条经验 获得超6个赞

我会加载到这个表中,然后为状态添加一列。默认情况下,您可以将此列设置为“未处理”。一旦线程开始处理该员工,它会将状态更改为“正在处理”,然后在完成后最终将状态切换为“已处理”。

拥有 3 个这样的状态还可以让您将其用作锁,防止处理发生两次。


查看完整回答
反对 回复 2023-03-02
  • 3 回答
  • 0 关注
  • 238 浏览

添加回答

举报

0/150
提交
取消
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号