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. ESP8266开发(物联网)

    使用开发板制作wifi干扰器https://www.jianshu.com/p/f064ca36ee92

  2. 2.21(html)

  3. c语言中的链表

    线性结构:有且只有一个根节点,且每个节点最多有一个直接前驱和一个直接后继的非空数据结构 非线性结构:不满足线性结构的数据结构 链表(单向链表的建立.删除.插入.打印) 1.链表一般分为: 单向链表 双 ...

  4. Vue+SSM+Element-Ui实现前后端分离(2)

    前言:后台使用ssm搭建,对以前学习知识的一个回顾,与此同时来发现自己不足.这里主要采用配置文件方式进行,有部分注解. 目标:搭建ssm框架,并测试成功:(其中也有aop切面的编写) 一.开发工具 I ...

  5. python跨文件之全局变量

    Python中的global关键字,你了解吗? - 知乎 (zhihu.com)  global 关键字 python跟C不一样,c是在一个文件定义后在另一个文件声明下是extern变量就好.pyth ...

  6. Kicad使用技巧--原理图复用

    平时主要使用AD.kicad和立创eda,最近在琢磨一下各个软件的使用技巧,提升一下画图效率,首先想到的就是原理图复用,我想象中的原理图复用应该像AutoCAD的图块功能一样. 这次先说kicad,摸 ...

  7. CentOS 7(Linux)安装docker,执行yum install docker-io -y报错

    CentOS 7(Linux)安装Docker,执行yum install docker-io -y报错 一.执行yum install docker-io -y报错 Error: docker-ce ...

  8. C语言程序设计基础 实验3 函数

    C语言程序设计基础 实验3 函数   一.实验目的 1. 理解函数的本质:模块化,实现代码复用 2. 掌握函数定义.声明.调用的语法 3. 理解并掌握函数的形参.实参,以及函数调用和返回的过程 4. ...

  9. Qt之如何创建并显示一个柱状图

    创建一个简单的柱状图 第一步:创建一个QBarSet对象:QBarSet类代表条形图中的一组条形. QBarSet *set0 = new QBarSet("Jane"); QBa ...

  10. Pytorch Chain-Rules

    Derivative Rules \[\begin{aligned} &\frac{\delta E}{\delta w^1_{jk}}=\frac{\delta E}{\delta O_k^ ...