ORSet

这段代码实现了OR-Set,是一种基于版本向量的CRDT,用于实现集合的合并。OR-Set由两个集合add和remove组成,add集合存储添加的元素,remove集合存储删除的元素。每个元素都有一个版本向量,用于标识该元素的添加和删除操作。其中,add集合中的元素版本向量的值大于remove集合中的元素版本向量的值,表示该元素是存在的。OR-Set支持添加和删除元素,以及合并两个OR-Set。其中,添加元素时,会将该元素的版本向量加1,删除元素时,会将该元素的版本向量加1并放入remove集合中。合并两个OR-Set时,会将两个OR-Set的add集合和remove集合分别合并,然后将remove集合中版本向量小于add集合中版本向量的元素从remove集合中删除,最后返回合并后的OR-Set。

import VClock

def ORSet():
return (dict(), dict()) def zero():
return ORSet() def value(s: ORSet):
add, rem = s
return {key for key in set(add.keys()) | set(rem.keys())
if VClock.compare(add.get(key, VClock.zero()), rem.get(key, VClock.zero())) != VClock.Ord.Lt} def add(s: ORSet, replica_id, value):
add, rem = s
add[value] = VClock.inc(add.get(value, VClock.zero()), replica_id)
print(add[value]) def rem(s: ORSet, replica_id, value):
add, rem = s
rem[value] = VClock.inc(rem.get(value, VClock.zero()), replica_id) def merge(s1: ORSet, s2: ORSet):
add_1, rem_1 = s1
add_2, rem_2 = s2 merged_add = { key: VClock.merge(add_1.get(key, VClock.zero()), add_2.get(key, VClock.zero()))
for key in set(add_1.keys()) | set(add_2.keys()) } merged_rem = { key: VClock.merge(rem_1.get(key, VClock.zero()), rem_2.get(key, VClock.zero()))
for key in set(rem_1.keys()) | set(rem_2.keys()) } cleared_merged_rem = { key: merged_rem[key] for key in set(merged_rem.keys())
if VClock.compare(merged_add.get(key, VClock.zero()), merged_rem[key]) == VClock.Ord.Lt or
VClock.compare(merged_add.get(key, VClock.zero()), merged_rem[key]) == VClock.Ord.Cc } return (merged_add, cleared_merged_rem)
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set; public class ORSet {
private Map<String, Map<Integer, Integer>> add;
private Map<String, Map<Integer, Integer>> rem; public ORSet() {
add = new HashMap<>();
rem = new HashMap<>();
} public static ORSet zero() {
return new ORSet();
} public Set<String> value() {
Set<String> res = new HashSet<>();
for (String key : add.keySet()) {
if (!rem.containsKey(key) || !compare(add.get(key), rem.get(key)).equals(Ord.Lt)) {
res.add(key);
}
}
for (String key : rem.keySet()) {
if (!add.containsKey(key)) {
res.add(key);
}
}
return res;
} public void add(int replica_id, String value) {
if (!add.containsKey(value)) {
add.put(value, new HashMap<>());
}
Map<Integer, Integer> clock = add.get(value);
clock.put(replica_id, clock.getOrDefault(replica_id, 0) + 1);
} public void rem(int replica_id, String value) {
if (!rem.containsKey(value)) {
rem.put(value, new HashMap<>());
}
Map<Integer, Integer> clock = rem.get(value);
clock.put(replica_id, clock.getOrDefault(replica_id, 0) + 1);
} public void merge(ORSet other) {
for (String key : other.add.keySet()) {
if (!add.containsKey(key)) {
add.put(key, new HashMap<>());
}
Map<Integer, Integer> clock = add.get(key);
for (Map.Entry<Integer, Integer> entry : other.add.get(key).entrySet()) {
int replica_id = entry.getKey();
int timestamp = entry.getValue();
clock.put(replica_id, Math.max(clock.getOrDefault(replica_id, 0), timestamp));
}
}
for (String key : other.rem.keySet()) {
if (!rem.containsKey(key)) {
rem.put(key, new HashMap<>());
}
Map<Integer, Integer> clock = rem.get(key);
for (Map.Entry<Integer, Integer> entry : other.rem.get(key).entrySet()) {
int replica_id = entry.getKey();
int timestamp =

实现一个CRDT工具库——ORSet的更多相关文章

  1. 如何手写一个js工具库?同时发布到npm上

    自从工作以来,写项目的时候经常需要手写一些方法和引入一些js库 JS基础又十分重要,于是就萌生出自己创建一个JS工具库并发布到npm上的想法 于是就创建了一个名为learnjts的项目,在空余时间也写 ...

  2. [js高手之路] 跟GhostWu一起封装一个字符串工具库-架构篇(1)

    所谓字符串工具库就是利用javascript面向对象的知识封装一个常用的字符串处理方法库,首先给这个库起个名字,好吧就叫ghostwu.js. 看下ghostwu.js的整体架构: ; (functi ...

  3. [js高手之路] 跟GhostWu一起封装一个字符串工具库-扩展trim,trimLeft,trimRight方法(2)

    我们接着上一篇的继续,在上一篇我们完成了工具库的架构,本文扩展字符串去空格的方法, 一共有3个 1,trimLeft: 去除字符串左边的空格 2,trimRight: 去除字符串右边的空格 3,tri ...

  4. [js高手之路] 跟GhostWu一起封装一个字符串工具库-扩展字符串位置方法(4)

    本文,我们接着之前的框架继续扩展,这次扩展了一共有5个与字符串位置相关的方法 between( left, right ) 返回两个字符串之间的内容, 如果第二个参数没有传递,返回的是找到的第一个参数 ...

  5. [js高手之路] 跟GhostWu一起封装一个字符串工具库-扩展camelize与dasherize方法(3)

    在此之前,我们已经完成了4个方法: trimLeft, trimRight, trim, capitalize 本文,我们扩展驼峰式与下划线转化这两个对称的方法 camelize: 把空格,下划线,中 ...

  6. 一个PHP高性能、多并发、restful的工具库(基于multi_curl)

    This is high performance curl wrapper written in pure PHP. It's compatible with PHP 5.4+ and HHVM. N ...

  7. Underscore.js工具库

    Underscore 是一个 JavaScript 工具库,它提供了一整套函数式编程的实用功能,但是没有扩展任何 JavaScript 内置对象. 他解决了这个问题:“如果我面对一个空白的 HTML ...

  8. JavaScript工具库

    jPublic 交流QQ群:1017567122 前言 在我们开发项目的时候,无论项目规模大小,在所难免会写一些工具型函数来解决一些问题,随着项目开发和维护的时间越来越长,这些工具型函数会越来越多,同 ...

  9. 手把手教你使用Rollup打包📦并发布自己的工具库🔧

    DevUI是一支兼具设计视角和工程视角的团队,服务于华为云DevCloud平台和华为内部数个中后台系统,服务于设计师和前端工程师. 官方网站:devui.design Ng组件库:ng-devui(欢 ...

  10. 自己的一个LESS工具函数库

    自己大概在一年前开始使用LESS编写样式,现在感觉不用LESS都不会写样式了.现在写静态页面完全离不开LESS与Zen Coding,我可以不用什么IDE,但这两个工具却必须要,当然也强烈推荐看到这篇 ...

随机推荐

  1. c语言实现单链表的倒叙

    bool upsidedown_list(LinkList L) { Lnode *head, *tmp, *oldhead; head = L; tmp = L->next; oldhead ...

  2. ethcat开发记录 一

    一.方案 1.移植开源方案SOEM 2.专用芯片 二.SOEM移植 (一)硬件 stm32f407,168M PHY:LAN8720A (ii) Points to note 1, the PHY a ...

  3. 平方损失函数为例的BP的关键公式推导

    看了刘建平老师的博客https://www.cnblogs.com/pinard/p/6422831.html对如下其中两个公式进行详细推导 损失函数为(大写字母为矩阵,小写字母字母加粗为列向量,其中 ...

  4. html input 属性

    一:disabled disabled 属性规定应该禁用 input 元素,被禁用的 input 元素,不可编辑,不可复制,不可选择,不能接收焦点,后台也不会接收到传值.设置后文字的颜色会变成灰色.d ...

  5. 关于LAB2中的assert

    在LAB2中,测试类里会看到这样一句话 注释的意思是确保VM参数启用 -ea,这是个新东西,平时也没写过,我们来了解一下. assert不同于assertEquals这样的函数,是Java中的一个关键 ...

  6. Gabor滤波(个人学习)

    Gabor滤波 1.优点 Gabor小波与人类视觉系统中简单细胞的视觉刺激响应非常相似.在提取目标的局部空间和频率与信息方面具有良好的特性. 对于图像的边缘敏感,能够提供良好的方向选择和尺度选择.因此 ...

  7. Offer 提速:如何写出有亮点的简历

    先来个灵魂拷问: 你与他人相比,有什么能形成明显区分度的优势条件? 这里有两个层面的问题,一是 如何识别出你的优势条件,毕竟大多数人大多数时候可能都是在做业务,临到写简历的时候要求总结日常工作中跟别人 ...

  8. PHP实现微信提现V3版本2022-5更新接口:商家转账到零钱

    微信官方又更新了接口... V3版本的微信商家转账到零钱的接口---俗称提现接口 注意事项 一:开通条件:需满足入驻满90天,连续正常交易30天,保持正常健康交易.二:分为页面发起和api接口操作,均 ...

  9. Vue Yarn npm nodejs - 安装、配置

    一.安装 node.js 1.从node.js官网下载并安装,安装时,安装路径可以修改为非C盘 2.使用 node --version 命令在 CMD 中查看 nodejs 安装的版本,显示了安装的版 ...

  10. git—分支设置

    什么是分支? 项目以上线,但需要开发新的功能.不能直接在项目上进行开发的,这时候就需要创建一个分支,去完成新功能的开发.测试等.完成之后合并到主分支上面.如果新功能的开发不用分支,导致的问题就会有很多 ...