CAP理论(分布式系统的引导式思想)

CAP理论

 

CAP理论,这篇文章的标题已经写好久了,一直想着学习一下什么叫CAP理论,但是这段时间一直在巩固JVM相关的知识,就没有穿插其他知识点的文章。

今天还是了解一下什么叫CAP理论吧!

 

关于此类偏理性的知识点,需要借助维基百科的定义作为我们的参考文献:

CAP定理

理论计算机科学中,CAP定理(CAP theorem),又被称作布鲁尔定理(Brewer's theorem),它指出对于一个分布式计算系统来说,不可能同时满足以下三点:[1][2]

  • 一致性(Consistency) (等同于所有节点访问同一份最新的数据副本)

  • 可用性Availability)(每次请求都能获取到非错的响应——但是不保证获取的数据为最新数据)

  • 分区容错性(英语:Network partition)(Partition tolerance)(以实际效果而言,分区相当于对通信的时限要求。系统如果不能在时限内达成数据一致性,就意味着发生了分区的情况,必须就当前操作在C和A之间做出选择[3]。)

根据定理,分布式系统只能满足三项中的两项而不可能满足全部三项[4]。理解CAP理论的最简单方式是想象两个节点分处分区两侧。允许至少一个节点更新状态会导致数据不一致,即丧失了C性质。如果为了保证数据一致性,将分区一侧的节点设置为不可用,那么又丧失了A性质。除非两个节点可以互相通信,才能既保证C又保证A,这又会导致丧失P性质。

 

上面说到一句话:在一个分布式计算系统中,不能同时满足:一致性、可用性、分区容错性;

我们需要通过这句话进行开展分析。

 

1.开展分析的前提条件,我们需要了解一下什么是分布式系统?

举个生活中的例子,我们一个小饭馆,通常来说就是一个老板,一个人经营了整个小店;老板要负责早上把当天需要的食材先购置好,然后做好配菜,切好。然后顾客进来后,需要点餐,收账,接着再炒菜等等事情。

我们可以理解:一个很小的饭店,基本上一个人可以解决。

但是当规模大了起来后,如果一个人去解决所有的事情,即使这个人很能干,也会出现问题,如果老板一个人一下干这干那,就会尽大限度的让老板一个人处于崩溃的边缘,如果老板吃不消了,那整个饭店的经营就会停止了。

那么到了一定规模后,通常老板会请人专门干活,例如会请配菜员专门切菜、请厨师专门炒菜、服务员专门收银等等,那么就会各司其职,形成一个专门的人干专门的活,这样每个人都会对自己干的事情有头绪,而不是一下干这,一下干那的。这种就是团队合作。

但是我们思考,似乎还有一个问题没有解决:假设厨师当天请假了?咋办?那么整个饭店经营还是进行不下去了。

我们可以想到,就是采用请多个厨师,即使,有一天有一个厨师请假了。另外一个,还可以支持一下,然后给予我们缓冲的时间。这样就是先保证饭店能开,能运作。

 

上述举例,其实就是一种单体应用服务向分布式系统服务的转变,我们将老板一个人的职责拆分为了多个方向的职责,然后分别交于不同的独立的系统去执行(员工),员工之间通过远程过程调用等通信方式进行沟通,原老板一个人收了饭钱,他知道要去炒菜了,就直接去了。现在不一样,收银员收了钱,就会把菜单作为纸条形式传递给后厨人员,然后收银员就继续专心的收银,就不管其他事情了,而后厨人员收到了菜单,就会制作,制作完成了就通知服务员进行传菜,然后厨师就不管这道菜后面的动作了。这种方式,通过分布式系统方式,将一个完整的动作拆分为多个大动作,让系统更加专注了。并且倘若说,这个时候,老板想加个活动的业务,就是在上菜的时候,需要我们吆喝一声,那么只需要对“传菜员”这个系统进行修改就可以了。而不需要影响“收银员”、“厨师”系统的正常运作。

 

那么随之现在互联网的系统架构都分布式化后,将各个系统间的职责模块化划分,就增加了系统的易扩展性,可靠性,可控性,可用性等等优势。但是随之也会带来一些问题;

什么问题呢?

那么就是各个系统间的同步问题,我们带着问题进行下面的分享。

 

 

2.先分析一下CAP

(1)一致性(Consistency):

怎么理解?就是需要分布式系统中所有的节点都在访问同一份最新的数据副本。就好比北京店的厨师又卖出一碗炸酱面,那么海南店的厨师算上卖了多少碗的时候,可能不会算上这一碗。那么分别问两位师傅一共卖了多少碗的时候,就会有两个结果了。那么怎么解决呢?就需要使用到“分区容错性”,由北京店厨师告诉海南店厨师,他刚刚卖了一碗。就一致了。

(2)可用性(Availability):

每次请都能获取到非错的响应---但是不保证获取的数据为最新。这一点似乎和第一中的一致性冲突了。就好比,所有节点获取数据,都能获取到,都不会说报错了,然后不返回数据了,只是可能节点1获取的数据是2秒前的最新数据,而节点2获取的数据是1秒前的最新数据,两者就不会相同。

(3)分区容错性(Partition tolerance):

实际效果而言,分区相当于对通信的时限要求。系统如果不能在时限内达成数据一致性,就意味着发生了分区的情况,那么就必须就当前操作在C和A中做出选择。

这句话怎么理解?就是一个分布式中的两个节点相互通信,可能会失败。就好比,我们北京店的厨师通知海南店的厨师,说他刚刚做了一个辣椒炒蛋。那么有可能这个通知就是失败的,到头来,海南店的厨师是不知道北京店的厨师做了“辣椒炒蛋”的。这种场景,我们认为,一定存在这样的概率(概率>0即为一定);

 

3.总结

上方的三个三角理论:所谓CAP理论,就是三者条件,只能存在2种同时成立。也就是我们选择满足其他两种,就会有一种不满足,而我们刚刚说的分区容错性,是必须要考虑的,就是节点间相互通信,我们必须要考虑其通信失败的情况。

那为什么说一致性和可用性不能同时满足呢?

假设我们强烈要求满足一致性,也就是说,我们北京店系统卖出的炸酱面,+1了后,通知海南店系统之前,如果有人问卖了多少碗,是不能告诉他的,只能在两个店都达成最新的数据共识后,才能准确的告诉别人。这个时候就违背了可用性的定理。

同理可得,可用性的定理就是违背了一致性的定理了,因为如果我们要优先保证系统的可用性,那么就会出现数据不一致的情况发生。

 

4.实例拓展一下思考:

看到cap定理是一个三角存在的定理,也就是说只能满足两者,那么我们怎么去实例中理解他呢?

假设一个系统强要求可用性。可以理解为一个“微博热搜实时排行榜”,我想问一下,如果两台手机同时刷新一下,获取最新的热搜数量的排行榜,两个内容会是完全一模一样的吗?如果是北美洲的用户和亚洲的用户同时刷新一下全球热搜排行榜,两个结果就是一致的吗?

很显然,不可能是一致的,但是作为这个业务而言,也不需要做到毫秒级别,秒级以内的一致性。那么这时候我们就会抛弃CAP定理中的c一致性,更多的满足可用性,不能说两个用户刷新一下,一个用户就失败了。我们需要优先保证系统的可用性。但是最终的结果,两个用户会刷新到最新的数据。

 

那么什么业务场景需要优先保证一致性呢?就好比存取钱。

之前在网络上看到这样一则帖子;

他说:我同时在银行存取款机取钱,然后同时用微信发个红包,那么是不是可以不断的刷钱??

先说明背景,微信红包系统,和银行存取款系统是两个完全独立的系统,是属于分布式系统中的范畴,那么是符合背景。那这个网友这种操作可行吗?当然不现实,两个动作,总归有先后,当第一个操作进入,第二个操作进只能被阻塞等待,这样当第一个操作完成后,第二个操作获取到数据,就是没钱了,那么这个时候,第二个操作必然是失败的。

这种场景就是需要要求强一致性,而我们就需要抛弃可用性,会在第二个操作的时候,返回错误给用户,达到一致性的目的。

 

那么我们能不需要保证分区容错性吗?从而达到CA的效果呢?

也就是说,我们需要达到一致性和可用性?

那可以理解为,我们抛弃了分区容错性,就是抛弃了分布式系统的架构模式,因为我们不想出现分区容错性的问题发生,那么就只能不出现分区,这样,在单体应用服务中,就不会出现这种问题,那么我们就可以保证一致性和可用性的。

但是这样是不是有违背我们上面的初衷?引入分布式的意义?

实际应用场景?我可能会想到一个工厂内部的系统运作,可能会抛弃系统的高并发压力优势,选择数据的强一致性和可用性。但是此处的可用性不是高可用。

 

5.总结笔者的心声

关于上述的CAP定理,是分布式计算领域的公认定理。是我们对于分布式架构的一种指明灯的设计思路的基本定理了。那么对于笔者所从事的互联网系统中,更多的是倾向于AP模式,也就是达到可用目的。

用户可能不在乎当前的文章的浏览量是10002次,还是10003次,但是用户在乎能不能正常浏览,我们程序设计者也在乎系统的分布式化能力。

 

 

6.贴上cap定理实现图示

 

 

 

已标记关键词 清除标记
相关推荐
©️2020 CSDN 皮肤主题: 程序猿惹谁了 设计师:白松林 返回首页