大家谈谈怎么保证数据的数据准确性和完整性

大家谈谈怎么保证数据的准确性 - ITeye问答
比如:我要进行数据库里一个字段是记录余额100,现在客户端进行购物,分别在不同机器上进行登录后,然后分别在两台机器上同时拍下两个物品,价格分别是100,100,此时余额只有100,如何避免100被扣减两次,貌似和并发差不多
不知道标题是否描述准确
核心确实是锁机制。一般Java ORM可以通过乐观锁来完成。纯SQl也可以使用数据库锁进行处理。
同时拍下两个物品是并发操作,而共享的资源是余额,在操纵余额的地方加上锁保护就可以了, 简单点的话直接在扣余额的方法加上synchronize修饰符
已解决问题
未解决问题2011年6月 Oracle大版内专家分月排行榜第三2011年5月 Oracle大版内专家分月排行榜第三
本帖子已过去太久远了,不再提供回复功能。如何处理微信的并发推送并保证数据的准确性 - 推酷
如何处理微信的并发推送并保证数据的准确性
并于并发处理的问题已不新鲜,网上也有大量的解决方案及一些开源的代码。最近做的一个项目也遇到了并发的问题,并不是前端请求并发,而是微信推送事件的并发,略坑。
关于微信并发
并发在很多系统中都存在,比如抢红世,秒杀商品之类的。
我们做了一个通过微信的摇一摇与用户进行互动的一个模块(需要摇一摇的周边产品),当用户摇一摇的时候触发微信通知。
若按照片微信官方文档写的应该是第一次推送失败后会再次进行推送,最多推送三次。只要在5秒内返回空字符串就行。
但根据我日志来看,微信在同一时间同时推送了两条一样的记录。并且还多次重现了,为了解决这个问题我们想了几种解决方案。
当然还有很多其他解决方案,我这里只写最简单的。
我猜想的微信摇一摇周边实现
微信通过蓝牙搜索附近一摇一摇周边的蓝牙设备,然后获取到设备的基本信息与微信服务器上所配制的信息进行匹配。再把用户信息及摇一摇事件信息推送的当时所配制的第三方服务的地址。这时候第三方服务器接收到用户标识(openid)与摇一摇周边设备的信息进行验证,这样用户是否是通过运营方的设备摇进来的并且做相关的操作。
那么摇一摇事件微信本身是做了限制的,根据我们的测试一个手机设备一分钟最多只能摇25次,超过将进行锁定,几分钟后将可以再次摇。
在我看来单个用户同一时间请求两次这应该是一种小概率事件,很奇怪微信没限制住还是其他什么原因。部份手机重现过。
本项目的技术架构
由于种种原因我们尝试了这种技术架构,感觉好像是前无古人。哈哈哈哈哈哈(自嗨一下)但这种架构也踩了不少坑,当然这也是好事,有坑就踩实了,为了让以后的项目更好的绕过一些没必要重复踩的坑。
主要业务由ngx_lua来实现所有的交互逻辑包括微信的事件处理及其他业务处理,websocket由golang来实现,后台php实现(主要做控制、配制、入库),数据库是由Redis作为主要业务, mysql做为数据存储。
ngx_lua处理并发的能力还是不错的,至少在4核8G的测试环境上看QPS到1000+应该是没啥问题的,因为大多数据操作或外网api请求都是异步完成的。主流程很少会出现阻塞。
这个项目的接口文档及数据结构文档已经超过20页了,是不是很6 =_= 嘿嘿!
并发就是在同一时间发起了多次请求,如果按正常处理的话。肯定会出现多次获取数据然后覆盖的问题。
若我们不对并发进行处理,那么很可能会出现一个商品被消费多次的情况。
为了模拟微信的这种事件推送,我用Python写了一个模拟并发请求的小工具:
通过python的多线程模拟同一时间多个post请求。
若无法查看,请点击下面的[查看原文]
我们知道Redis是单进程、单线程的程序。那么它是阻塞的,既然是阻塞的,那么就很好处理了。
比如队列、锁、事物,都能很好的处理并发问题,若是多线程的程序那么处理起来会比较麻烦一些。
当然也有组合的方式,比如下面我们所使用的就是组合的方式处理的。
队列相对来说是一种相对来说比较安全的处理方式,但是它的弊端就是&慢&,数据得一个一个出,一个一个处理,这可以保证数据的准确性,但若数据量实在太大的话数据会堆积越来越多,那么最后入的数据可能会等的时间会长一些才能被消费掉。
当然这种方案也适合在某些场景。
消费队列很重要,做好控制。
并发锁其实是一个不错的方案,至少我是这么觉得的。因为我这是我目前的解决方案。
那为啥用“锁”的机制呢?
因为这样我不用改太多的代码呀,并且还能保证高效....何乐而不为呢?( ̄▽ ̄)
如果前面没控制好,再使用队列的话,那么就有可能有多个相同的数据被消费.
锁的正确使用方式
Redis 里有一个命令叫作 SETNX , SETNX 有一个内部锁的机制,咱们可以利用它这一特性。当写入某个key 的时候 如果key存在,则返回0否则返回1 如果返回0跳出就行了,redis是单进行程单线程,那么同一时间只会有一个写,理论上来说不会出现两个或多个同时写一个key的情况。
那么如果加锁了,那就很有可能会出现死锁的情况,解决死锁的方法也很简单,那就是给这个锁加一个时间,若超过这个时间了,那么这个key就消失了,当然这得根据实际业务来写死锁的时间。
简单的伪代码
SETNX lock:test:{userId} hello // 根据用户id写入一个key若返回0 表示key已存在
EXPIRE lock:test:{userId} 5 // 给这个锁一个时间 咱们设置为5秒
HGET user:award {userId}
// 若已存在 删除锁 并跳出
RPOP award:list // 弹出消费
HSET user:award {userId} {AwardInfo}
// 若业务已处理完,只要把锁删掉就行了 这样锁就释放了
DEL lock:test:{userId}
这样就能保证单个用户,同时或在规定的时间内只操作一次。
那么后续的流程就需要队列了。
比如上面拦死后,我们就需要从队列里弹出理个值,进行验证,如果为空则跳出,不再继续了否则继续后续流程。
RPOP your:queue
通过这种简单的组合方式就可能保证数据的准确及效率了。
前者保证生个用户同时只能发起一个请求,后者保证仓库数值不会被多消费, 其实就是库存的问题。
事物的处理方略复杂些,在大多数据库都自带有事物实现,Redis本身没有,但可根据事物的机制自己实现一套,原理是一样的。
一会还有事,先偷个懒就不写了(反正你们也不知道我用没用过)
关于并发处理,欢迎大家提出问题,或提供其他解决方案。
写一个功能,能出问题就好,若出没遇到过的问题那是更好。当把一个非常难的问题解决之后的喜悦应该是非常有成就感的,非猿猿们可能体会不出这种喜悦。
同时感谢同事们的测试,感谢同事们的问题复现从而让我发现程序一些不够周全的地方。
最后,微信的服务也不是完全可靠的,大家注意着点。
已发表评论数()
请填写推刊名
描述不能大于100个字符!
权限设置: 公开
仅自己可见
正文不准确
标题不准确
排版有问题
主题不准确
没有分页内容
图片无法显示
视频无法显示
与原文不一致谈谈提高输入数据正确性的方法
&|&&|&&|&&|&&|&&|&&|&&|&&|&&|&&|&&|&
& 今天是:&&& 欢迎您光临[3edu教育网]!本站资源完全免费,无须注册,您最希望得到的,正是我们最乐于献上的。
◆您现在的位置:&&>>&&>>&&>>&&>>&&>>&论文正文
谈谈提高输入数据正确性的方法
谈谈提高输入数据正确性的方法
&&&&将本站加入收藏,以便日后访问。&&&&
谈谈提高输入数据正确性的方法
张正武 (合肥工业大学计算中心)
本文主要讨论提高输入数据正确性的方法,供读者参考与借鉴。
关键词:数据输入 数据校验 双工输入 加权求和
在数据库管理系统输入模块的开发中,如何提高输入数据的正确性是开发者应考虑的一个重
要问题。为了提高输入数据的正确性,其基本的功能要求是:①输入操作简单、轻松;②输
入效率高,即具有重复内容自动复制和简易代码输入替代功能;③输入格式美观大方;④具
有醒目的提示等。然而,仅有这些功能要求是不够的,它们不能从根本上提高输入数据的正
确性。因为,大量的原始数据的输入是件繁琐而又单调的工作,难免出错。所以,必须要有
更严格、更有效的科学方法和手段来提高输入数据的正确性。本文给出了提高输入数据正确
性的方法,供数据库管理系统的开发者参考与借鉴。
二、输入数据的校验与查错方法
输入数据的校验与查错方法常常有两种,其中第一种是边输入边校验法。在这种方法中,假
若输入数据有错,则要求数据录入者立即更正错误。这种方法常常用于所输入的数据具有某
种规律和特征,若数据录入者键入的数据违背了这个规律和特征,即立即给出输入出错警告
,并强制性要求数据录入者对当前输入的数据给予修正。例如,在财务管理系统中,一张“
记帐凭证”一般有借方金额和贷方金额两栏数字。会计制度要求同一张凭证中借方金额合计
和贷方金额合计必须相等。根据这一特征,所以在开发“记帐凭证”数据输入程序时,程序
应能自动判断,在一张“记帐凭证”的数据输入结束后,借方金额合计与贷方金额合计是否
相等,若不相等,应强制要求数据输入者立即重新输入。又例如,在每年的高考中,考生的
成绩数据有一部分要通过人工阅卷评分后,然后由专人输入计算机。对于考生成绩数据,它
所具有的特征是:每题的最高分和最低分(零分)是确定的,并且均为数字字符。根据这个特
征,所以在开发的考生成绩数据管理系统的输入模块中,应具有如下功能,即在每题数据输
入结束后,自动判断输入的分数值是否符合上述规律,若不符合,则应立即发出警告,并强
制要求录入者重新输入。
数据校验与查错的第二种方法是双工输入比较法。所谓双工输入比较法,就是将同一批数据
由两个输入人员在不同的时间和不同的终端上分别录入,并且形成两个临时数据库文件,然
后由第三个人在程序的作用下对两个库文件中的数据进行逐项比较并进行确认或修改。在这
种方法中,尽管同一批数据被录入了两次从而造成了数据冗余和影响了录入进度,但对于被
录入的数据不存在明显的规律和上述第一种方法不能查出输入出错的场合,以及对输入数据
的正确性要求很高的场合,是一种不可缺少的和行之有效的方法,因为,两个数据录入者都
同时在某处出错的机会极少,故这种方法可以极大地减少出错率。根据概率论原理,如果两
个数据录入者各自的出错率为百分之一,则双工输入法的出错率仅为万分之一。双工输入比
较法在FoxPro环境下的基本算法是:
①将同一批数据由两个录入者在不同时间和不同的终端上录入,并存入两个不同名
的库文件中。
②输入“①”中产生的两个库文件名。
③在两个工作区中分别打开一个库文件,并按记录号使两个库文件建立关联。
④对两个库文件中的对应记录进行逐项比较,若不相等,则进行登记,包括位置的登记。
⑤若记录未结束,则记录指针加1,转④。
⑥打印输出所有不相等的数据项及其位置。
⑦确认和修改。
在上述算法“④”中,若一个记录中的同类型的数据项很多,则程序往往显得冗长。为了解
决这个问题,可以把一个记录中同类型的数据项值加在一起求和,然后对求和结果进行比较
。这样,可以大大减少程序中关系表达式的数目,从而简化了程序并提高了程序的执行速度
。但此时最好用加权求和的方法。因为,含有相同数据类型、相同数据项个数的两次录入的
数据,其求和结果相等和并不等于两次录入的数据的对应项也相等,如表1所示。
表1:考生部分题的成绩数据双工录入对照表
第二题(权:3)第三题权
:2第四题权:1求和
不加权加权
第一次录入 25&& 15&& 10&& 50 &&& 115
第二次录入 15&& 25&& 10&&& 50 &&& 105
从表1可以清楚地看出,尽管第二次录入时把第二、三题的数据顺序输入反了,其和值
仍是50。若将第二、三、四题的得分值分别对应乘以位权3、2、1后再相加,就能发现两次
录入的求和结果不相等。这样就可查出第二、三题的数据错位。而这种数据错位错误在有些
实际问题中也是不允许的。
以上讨论的两种数据校验与查错方法,有时可以结合起来使用,即先用边输入边校验的方法
进行第一次把关,滤去误输入的错误数据。然后再用双工输入校验法进行第二次把关,第一
步校正误输入的错误数据。这样,可以确保输入的原始数据的正确。
三、结束语
在数据库管理系统的输入模块开发中,为了提高入库原始数据的正确性,数据的校验与查错
功能是不可缺少的。回顾我单位近四年(95~98年)承担的安徽省高考人工阅卷考生成绩的录
入与管理,由于采取了一系列行之有效的措施,特别是采用了本文给出的提高输入数据正确
性的方法,所以,连续四年未发现考生成绩输入错误。受到了安徽省教委有关部门的表扬。
《谈谈提高输入数据正确性的方法》一文由3edu教育网www.3edu.net摘录,版权归作者所有,转载请注明出处!
【温馨提示】3edu教育网所有资源完全免费,仅供学习和研究使用,版权和著作权归原作者所有,如损害了您的权益,请与站长联系修正。
上一篇论文: 下一篇论文:

我要回帖

更多关于 保证报道准确性 的文章

 

随机推荐