并发控制方式的选择

  1. 事务隔离(针对可重复读和串行化级别)

mysql使用的是二阶锁方案。得到锁之前会一直等待,这种方式的缺点是性能不好,优点是不需要失败后重试。属于悲观锁方案。
postgresql使用的是SSI——Serialized Snopshot Isolation,任何操作不需要等待,但是提交数据时若检测到数据有冲突会抛出异常并回滚。优点是不会出现死锁,缺点是当失败时需要不断重试,当失败的次数比较多时频繁重试会大量消耗性能。属于乐观锁方案。
引用
//www.greatytc.com/p/cb97f76a92fd
文中的一段话

在MySQL中,很多开发者倾向于自己在默认隔离级别之外手工加锁。而PostgreSQL则建议尽量避免直接加锁,因为其Repeatable Read和Serializable的实现已经相当完善,开发者没必要自找麻烦。

  1. 显式指定数据库行锁

人工给记录加锁,当然人工处理锁问题自然是比较麻烦还容易出错
mysql可用这种方式

  1. php处理

对于yii2框架来说ActiveRecord中已经集成了乐观锁的功能,悲观锁需自己或参考第三方实现
具体参考这篇文章
http://www.digpage.com/lock.html
如果用mysql数据库可以考虑这种方式,只是性能会比数据库行锁低一些。

  1. 业务级控制

redis锁,postgresql的advisory lock
这种主式比较灵活,需要自己控制,用的好可以实现性能最优,用不好也会性能比较差。单纯从锁性能来说应该是以上三种方案的。

关于秒杀的问题

秒杀的场景通常是有限的商品海量的人员去争抢,能抢到手的通常只有前几名人员。

  • 如果是悲观锁方案,所有人(不管抢到没抢到)都会等待获取锁,直到超时结束。这会让没有抢到人的做不必要的等待。这个用无等待锁即可,直接返回请重试或抢购结束。
  • 如果是乐观锁方案,所有人(不管抢到没抢到)都会去提交事务,这会浪费不必要的系统资源,使系统卡住。即使不重试也需要事务回滚,没有想到很好的避免方法。
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容