p*****c 发帖数: 2858 | 1 其实这个问题应该发去database版,但是这里人气旺些,希望大家指点一下。
用例是一个库存系统,要实现乐观锁。
假设数据表3个字段: id , qty , version
要扣n个库存。
我放狗搜了一下,其他人的实现方法都是
1.select qty,version from stock where id=xxx;
取出version 赋值给$version.
2.update set qty=qty-n,version=version+1 where id = xxx and version = $
version;
我觉得引入version这个字段完全没有必要。
改成这样
1.select qty from stock where id = xxx;
取出qty 赋值给$qty
2.update set qty = qty-x where id = xxx and qty = $qty;
不知道这样实现会不会有什么问题? |
R*********4 发帖数: 293 | 2 你想想 要是小明 和 小李同时操作
没有version 的,小明和小李都可以update 数据库
有version 的, 只有一个人可以操作。因为有一个人update 后version ,自加一了。 |
w**z 发帖数: 8232 | 3 通常
没有version,
a 读
b 读
a 写
b 写
b 把 a 的 覆盖了,而且不知道。
你还有一个 条件 qty, 除了这个还有其他 field 吗?
【在 p*****c 的大作中提到】 : 其实这个问题应该发去database版,但是这里人气旺些,希望大家指点一下。 : 用例是一个库存系统,要实现乐观锁。 : 假设数据表3个字段: id , qty , version : 要扣n个库存。 : 我放狗搜了一下,其他人的实现方法都是 : 1.select qty,version from stock where id=xxx; : 取出version 赋值给$version. : 2.update set qty=qty-n,version=version+1 where id = xxx and version = $ : version; : 我觉得引入version这个字段完全没有必要。
|
h**********c 发帖数: 4120 | 4 乐观锁
英语是什么,对我来说是新鲜事物,急需扫盲? |
g*******r 发帖数: 1414 | 5 OptimisticLock
【在 h**********c 的大作中提到】 : 乐观锁 : 英语是什么,对我来说是新鲜事物,急需扫盲?
|
l****r 发帖数: 105 | 6 以前公司用timestamp而不是version,不过我觉得GUID之类的token能更好地避免重复
回到正题,如果像lz说的不用version而是用qty的话,
没办法控制qty被别人改过然后又改回去的情况。
如果上述情况系统不需要关心的话那就没问题。
【在 p*****c 的大作中提到】 : 其实这个问题应该发去database版,但是这里人气旺些,希望大家指点一下。 : 用例是一个库存系统,要实现乐观锁。 : 假设数据表3个字段: id , qty , version : 要扣n个库存。 : 我放狗搜了一下,其他人的实现方法都是 : 1.select qty,version from stock where id=xxx; : 取出version 赋值给$version. : 2.update set qty=qty-n,version=version+1 where id = xxx and version = $ : version; : 我觉得引入version这个字段完全没有必要。
|
p*****c 发帖数: 2858 | 7 是的,在我理解中。
库存系统应该不需要担心改过被改回去的问题。因为要么是加,要么是减。
比如说3个订单,订单A 减 1 , 订单B 被取消 所以 加1 , 订单c 减1.
如果原QTY 是 10,不管如何并发操作,正常结果是9.
我的预想就是设置一个事务流程
1. begin transaction
2. select qty
3. update stock when id = xxx and qty = $qty
4. get affect row
5. if affect row >0 then commit else rollback
update是原子操作,如果条件不对就不会执行
当然我也不理解如果库存系统的数据表要加version这个字段是不是还有其他作用,我
只是觉得为了实现乐观锁是不需要这个字段。
【在 l****r 的大作中提到】 : 以前公司用timestamp而不是version,不过我觉得GUID之类的token能更好地避免重复 : 回到正题,如果像lz说的不用version而是用qty的话, : 没办法控制qty被别人改过然后又改回去的情况。 : 如果上述情况系统不需要关心的话那就没问题。
|
R*********4 发帖数: 293 | 8 作为unique的东西,最好设置只能往上加。我说实话,没看到您的qty,但是那是没意
义的。仓库的管理,qty本身就是可以加也可以减的,我没见过哪个仓库只卖东西,不
进库的。
我给很多shoot range做过inventory。里面的要求就是,即使每次staff哪怕点击了add
或者remove那个按钮,就算没有最后操作,流程都要求version自加。
我给你范例吧,你自己瞧瞧,只是范例,解释为什么。
A, B staff同时获得version,但是不同时操作第二步。
A staff
【1】qty - n
【2】发现错误,cancel, qty + n, qty恢复到回来的值。
大概几秒钟后,B staff开始操作了。
【1】qtfy - n,
因为A的【1】操作,影响了version, A staff把qty恢复到了以前的值了,B staff的
qty相同,但是version不同。
其实也可以记住时间,但是没必要,我发现很多inventory都是自加的。 |