【小优化】golang中取两个字符串的公共前缀的长度
作者:张富春(ahfuzhang),转载时请注明作者和引用链接,谢谢!
在VM的merge部分的代码中发现这样一个函数:
func commonPrefixLen(a, b []byte) int {
i := 0
if len(a) > len(b) {
for i < len(b) && a[i] == b[i] {
i++
}
} else {
for i < len(a) && a[i] == b[i] {
i++
}
}
return i
}
在merge整个sstable的时候,需要算出所有字符串的公共前缀,然后存储的时候就不再存储公共前缀的部分,这样就实现了进一步的数据压缩。
这个函数调用得非常频繁,于是想尝试用SIMD来优化。
后来试了一下,简单的写法就能提升1.6倍,优化的代码如下:
// macbook pro 2019, Intel(R) Core(TM) i7-6700HQ CPU @ 2.60GHz
// 15.70 ns/op
func commonPrefixLenOneByOne(a, b []byte) int {
i := 0
if len(a) > len(b) {
for i < len(b) && a[i] == b[i] {
i++
}
} else {
for i < len(a) && a[i] == b[i] {
i++
}
}
return i
}
// from this issue: https://github.com/VictoriaMetrics/VictoriaMetrics/issues/2254
// macbook pro 2019, Intel(R) Core(TM) i7-6700HQ CPU @ 2.60GHz
// 9.785 ns/op when memory aligned, 1.6 times faster
// 9.833 ns/op when memory not aligned
func commonPrefixLen(a, b []byte) int {
if len(a) > len(b) {
a, b = b, a
}
if len(a) < 8 {
return commonPrefixLenOneByOne(a, b)
}
const size = 8
compareTimes := len(a) / size
addrA := uintptr(unsafe.Pointer(&a[0]))
addrB := uintptr(unsafe.Pointer(&b[0]))
for i := 0; i < compareTimes; i++ {
v1 := (*uint64)(unsafe.Pointer(addrA))
v2 := (*uint64)(unsafe.Pointer(addrB))
if *v1 != *v2 {
return i*size + commonPrefixLenOneByOne(a[i*size:], b[i*size:])
}
addrA += size
addrB += size
}
return compareTimes*size + commonPrefixLenOneByOne(a[compareTimes*size:], b[compareTimes*size:])
}
思路就是用unsafe指针把连续的8个byte转换为uint64的指针,这样就可以一条指令比较8个字节。
这个优化已经提了一个PR到VM的仓库:https://github.com/VictoriaMetrics/VictoriaMetrics/pull/2913
【小优化】golang中取两个字符串的公共前缀的长度的更多相关文章
- JS 从一个字符串中截取两个字符串之间的字符串
/************************************************* 函数说明:从一个字符串中截取 两个字符串之间的字符串 参数说明:src_str 原串, start ...
- Java 中如何计算两个字符串时间之间的时间差?(单位为分钟)
Java 中如何计算两个字符串时间之间的时间差?(单位为分钟) import java.text.DateFormat; import java.text.ParseException; import ...
- golang中判断两个slice是否相等
在golang中我们可以轻松地通过==来判断两个数组(array)是否相等,但遗憾的是slice并没有相关的运算符,当需要判断两个slice是否相等时我们只能另寻捷径了. slice相等的定义 我们选 ...
- SQL Server中取两个表的交集,并集和差集
在项目中遇到要取两个表差集的情况 假设有两个表tblNZPostCodes, NZPostcode 两个表中存储的都是新西兰的post code信息,字段一致,只是数据上有所差异. 1. Union ...
- java中判断两个字符串是否相等的问题
我最近刚学java,今天编程的时候就遇到一个棘手的问题,就是关于判断两个字符串是否相等的问题.在编程中,通常比较两个字符串是否相同的表达式是“==”,但在java中不能这么写.在java中,用的是eq ...
- SQLServer中求两个字符串的交集(字符串以符号分隔)
两个字符串,以特定符号分隔(例如‘,’号),求交集 第一种情况: declare @m varchar(100),@n varchar(100)select @m=',2,3,5,7,8,9,10,' ...
- 字符串的公共前缀对Mysql B+树查询影响回溯分析
年前项目组接微信公众号. 上线之后,跟微信相关的用cid列的查询会话的SQL变慢了几十倍!思考这个问题思考了非常久.从出现以来一直是我心头的一个结.cid这一列是建了索引的,普通的cid列更新 ...
- Java 中字两个字符串判断是否相等(转载)
java中判断字符串是否相等有两种方法:1.用"=="运算符,该运算符表示指向字符串的引用是否相同,比如: String a="abc";String b=&q ...
- js-获取两个字符串日期的相隔周
例如说"2017-04-01 23:00:00"是周六, "2017-04-28 23:00:00"是周五,包含各自所在的那一周,我真正需要获得的结果是5个周. ...
- 将从数组中取到的字符串赋值给了UIImage导致的错误
Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[__NSCFConstantStr ...
随机推荐
- 海量数据分析快准稳!GaussDB(for MySQL) HTAP只读分析特性详解
摘要:除了拥有 ClickHouse 本身的极致性能外,GaussDB(for MySQL)的HTAP只读分析在 MaterilizeMySQL引擎的性能和稳定性等方面具有更优秀的表现,为提供更快更准 ...
- 万字保姆级长文——Linkedin元数据管理平台Datahub离线安装指南
元数据管理平台Datahub最近的热度越来越高.已经更新到了0.8.40的版本,来咨询我的小伙伴也越来越多,特别是安装过程有很多问题. 考虑到有些企业部分数据服务是部署在内网的,那么离线安装D ...
- 让 K8s 更简单!8款你不得不知的 AI 工具-Part 1
介绍 最近,AI 引起了广泛关注,而 Kubernetes 驱动的 DevOps 也不例外.软件工程师是自动化的忠实拥护者,因此针对 Kubernetes 操作员的 AI 驱动工具自然也开始涌现. 这 ...
- Kubernetes(K8S) 监控 Prometheus + Grafana
监控指标 集群监控 节点资源利用率 节点数 运行Pods Pod 监控 容器指标 应用程序 Prometheus 开源的 监控.报警.数据库 以HTTP协议周期性抓取被监控组件状态 不需要复杂的集成过 ...
- 一个IT老码农的创业和生活(一)抑郁和自杀
2019年2月18日,离我的38周岁生日还差两个月,我的编程培训班"源栈"开张了. 在此之前,从我2002年大学毕业,6年时间,我先后做过英语教师.实习律师.公司法务.装修公司 ...
- 一个非常轻量级的 Web API Demo
一个非常轻量级的 Web API Demo,代码量很少,实现了方法拦截器,token校验,异常拦截器,缓存 创建项目:如果选择Web API,项目中东西会比较多,这里选择Empty,把下面的Web A ...
- JSP | IDEA 配置 JSP 模板
新建 jsp 文件时的模板 在第 5 步输入下面模板代码: <%-- Created by IntelliJ IDEA. User: ${USER} Date: ${DATE} Time: ${ ...
- Kafka 原理以及分区分配策略剖析
一.简介 Apache Kafka 是一个分布式的流处理平台(分布式的基于发布/订阅模式的消息队列[Message Queue]). 流处理平台有以下3个特性: 可以让你发布和订阅流式的记录.这一方面 ...
- 写了个移动端可滑动(惯性滑动&回弹)Vue导航栏组件 ly-tab
https://www.imooc.com/article/23768?block_id=tuijian_wz https://blog.csdn.net/weixin_44614772/articl ...
- kubernetes scc 故障排查小记
1. 故障现象 环境在跑自动化测试时打印 error: [ ERROR ] Opening output file '/output.xml' failed: Read-only file syste ...
