Paxos算法 实例 时序图

脑图:算法说明

里面有好几个算法说明

http://naotu.baidu.com/file/584323ee64d5ce77a926915e7752d287?token=4bd4b488beb80e0e

实例1

 

下面画个时序图来加深理解

以这个实例画时序图

https://zh.wikipedia.org/zh/Paxos%E7%AE%97%E6%B3%95#.E5.AE.9E.E4.BE.8B

 

其中A1能和A2 A3通信,A5能和A2 A3通信

 

A1(Proposer),想把v修改成A1

A2(Acceptor)

A3(Acceptor)

A4(Acceptor)

A5(Proposer),想把v修改成A5

A1、A5提出proposal

发送:Proposal:{n=1}

 

 

 

 

发送:Proposal:{n=2}

A2、A3收到A1

A3、A4收到A5

其中A3先收到A1后收到A5

 

收到:Proposal:{n=1}

回应:Promise不接受小于1的proposal

收到:Proposal:{n=1}

回应:Promise不接受小于1的proposal

收到:Proposal:{n=2}

回应ok

回应:Promise不接受小于2的proposal

 

A1收到了过半数Promise,可以发送Accept请求

发送:Accept:{n=1,v=A1}

 

 

 

 

A2、A3收到Accept请求,也没啥问题,修改v

A4收到Accept请求,没啥问题,修改v

 

收到:Accept:{n=1,v=A1},将v修改从A1,并返回ok

收到:Accept:{n=1,v=A1},将v修改从A1,并返回ok

 

 

A3后收到了A5,需要告诉A5说自己曾经接受了A1

 

 

收到:Proposal:{n=2}

回应ok

回应:Promise不接受小于2的proposal,而且我曾经接受过{n=1,v=A1}的Proposal

 

 

A5收到了A3 A4的Promise请求

 

 

 

 

收到A3的请求里说他曾经接受了Proposal{n=1,v=A1},那我不能将v修改成我原来想修改A5了,还是修改成A1吧。发送:Accept{n=2,v=A1)

A4 A5收到A3的Accept请求

 

 

收到:Accept:{n=2,v=A1},将v修改从A1,并返回ok

收到:Accept:{n=2,v=A1},将v修改从A1,并返回ok

 

于是大家伙的v都等于A1了。

 

 

 

 

 

实例2

再看一个大神的例子巩固一下:​ Raft作者讲解Paxos 

首先,这是一个类似2阶段提交的算法:包括:Prepare、Accept

  • 大神定义了一个proposal Number = 当前是第几轮RoundNumber + Server Id
  • 大的priority number的优先级更高
  • Proposer有可能选择一个比他之前使用的更高的proposal number。
  • 每个server都要保存一个maxRound:当前自己看到的最大轮数
  • 如果要产生一个新的proposal number,那就需要:
  • maxRound++,然后拼接自己的server id
  • 这个maxRound需要持久化到硬盘里,在crash/重启之后不能复用原来的。

算法流程

ProposersAcceptors
1、选择proposal number:n 
2、广播Prepare(n)到所有servers 
 

3、回复Prepare(n):承诺不会接受<n的Proposal

如果n>minProposal,那就设置minProsal=n

Return(acceptedProposal, acceptedValue)

4、当收到大多数的回复:

如果有人返回了acceptedvalue,将value替换成最大的accetedValue

 

 
5、广播Accept(n, value) 

 

6、回复Accept(n, value)

如果n>=minProposal那么

AcceptedProposal = minproposal = n

acceptedValue = value

 

Return(minProposal)

 

7、当收到大多数回复:

看下是否有拒绝?(result > n?) 拒绝的话就返回到1(需要更新当前见过的最大的round,下次就更有机会赢了)

否则,就选好了新的value。

 

Acceptors必须将minProposal(承诺不可以Accept小于minProposal这个的Proposal)、acceptedProposal、acceptedValue保存在可靠存储中(硬盘)

 

开始举例子

例子1:

之前的value已经选好了,新的Proposer应该发现并且使用

注:

P3.1 表示 Proposal(n=3.1),ProposalNumber=3.1;  3:第三轮; 1:serverId=1

A3.1 X 表示 Accept(n=3.1, v=X) , ProposalNumber=3.1, 提交的value=X

过程:

server1作为Proposal 提出提案:P3.1, 得到了server1-3的回应,于是发出 A3.1 X

然后这个时候,server5也提出提案:P4.5;server5 本来想设置value=Y的,他先发出P4.5,server3收到之后,返回了他Accepted的Proposal(3.1)和Value(X);server5收到server3的response,发现有人返回了acceptedValue,于是发Accept请求的时候,value不再是原来想发的Y,而是改成了X,发出了A 4.5 X

 

例子2:

前一个value没有被选定,但是新的proposer看见了

server1提出提案P3.1 ,想设置value=X ,收到了server1-3的回复 然后发出A3.1 X;

server5提出提案P4.5,想设置vallue=Y,收到了server3-5的回复,同上,server3已经Accept3.1X了,所以会给sever5返回曾经accept的X,server5将value改成了X,发出A4.5 X;

这时候server1和server2才收到A3.1X,但是没关系,大家都会设置好value=X

 

例子3

后面的Proposal prepares

前面的流程都一样,不一样的地方在于,server3先收到A3.1 X,这时候由于server3 Promise了,他见过4.5了(minProposal=4.5),不会accept <4.5的Proposal,而且会把minProposal=4.5返回给server1,server1就可以发现自己失败了,需要重新来过;

然后A4.5Y到了,这时候可以接受,于是server5发出的A4.5 Y,得到了server3-5的accept

 

!!!!!!!!!可以看到!!!关键的步骤在于,如果关键的角色server3,在A3.1X之前收到了一个P4.5,P的Proposal number比较大,他就会拒绝A3.1X,然后原来提出的A3.1X的server1就需要重试

 

有时候会陷入死循环:

server1提出P3.1,server5提出P3.5,关键的角色是server3,server3收到了A3.1X,3.1<3.5,拒绝:

server1重新来过,提出P4.1,server3收到A3.5Y,但是3.5<4.1,再拒绝,server5重新来过:

根本停不下来。

 

解决方案:每次重试的时候随机地延时一下,给别的proposer一个机会完成choosing。

或者使用Multi-Paxos,选个leader来搞。

注:只有proposer知道哪个value被chosen

如果其他server也想知道,需要自己执行一遍paxos协议,发起自己的proposal。

 

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值