
数据结构与算法
文章平均质量分 68
chuixue24
这个作者很懒,什么都没留下…
展开
-
logn的感性认识
二分查找的时间复杂度是logn,假设问题规模是100万的数据,要查找的数字不在这100万数据内,最终需要的查找次数是log100万。也就是说利用二分查找,从100万的数据规模内,查找一般,最终需要的次数是20。每次查找,问题规模减半,2的x次方=100万,x的解近似是20。原创 2024-02-21 15:15:33 · 464 阅读 · 0 评论 -
常见数据结构详细图解、树的高度、深度、层数、跳表、二叉搜索树、平衡二叉树、红黑树、B树、B+树
二叉搜索树也叫二叉查找树。它是一种比较特殊的二叉树。转载 2024-02-21 12:32:50 · 1548 阅读 · 0 评论 -
跳跃表的原理和实现(Java)
/ data// links可以看到节点模型主要分为2个部分。data 部分包含具体的存储数据,这里为了不引入其他杂乱的问题,使用 Integer 作为 key 的类型,Object 作为value 的类型。links 部分包含4个指针,分别是 up、down、left、right,单从名字上就能够明白它们的作用。转载 2024-02-21 12:12:22 · 250 阅读 · 0 评论 -
【数据结构】红黑树与跳表
skiplist本质上也是一种查找结构,用于解决算法中的查找问题(Searching),即根据给定的key,快速查到它所在的位置(或者对应的value)。我们在《Redis内部数据结构详解》系列的第一篇中介绍dict的时候,曾经讨论过:一般查找问题的解法分为两个大类:一个是基于各种平衡树,一个是基于哈希表。但skiplist却比较特殊,它没法归属到这两大类里面。转载 2024-02-21 11:05:58 · 396 阅读 · 0 评论 -
为什么Redis不直接使用C语言的字符串
众所周知Redis有以下几种常见的数据类型 String(字符串)、List(列表)、Set(集合)、Hash(哈希)、Sorted set(有序集合)、Stream(流)、Geo(地理空间索引)、Bitmap(位图)、HyperLogLog(基数统计)等。我们最常用的就是String(字符串)类型,String类型既可以存储字符串,也可以存储数字,甚至可以直接进行数值运算。转载 2023-04-21 09:07:03 · 174 阅读 · 0 评论 -
BlockingQueue阻塞队列的实现原理
ArrayBlockingQueue基于数组实现的阻塞队列,创建队列时需指定容量大小,是有界队列。ArrayBlockingQueue底层采用循环队列的形式,保证数组位置可以重复使用。ArrayBlockingQueue存取都采用ReentrantLock加锁,保证线程安全,在多线程环境下也可以放心使用。使用ArrayBlockingQueue的时候,预估好队列长度,保证生产者和消费者速率相匹配。转载 2023-04-21 09:10:27 · 257 阅读 · 0 评论 -
常见限流算法及其简单实现
计数器法计数器法是限流算法里最简单也是最容易实现的一种算法。比如我们规定,对于A接口来说,我们1分钟的访问次数不能超过100个。那么我们可以这么做:在一开始的时候,我们可以设置一个计数器counter,每当一个请求过来的时候,counter就加1,如果counter的值大于100并且该请求与第一个 请求的间隔时间还在1分钟之内,那么说明请求数过多;如果该请求与第一个请求的间隔时间大于1分钟,且counter的值还在限流范围内,那么就重置 counter。具体算法的伪代码: /**原创 2022-04-19 14:23:21 · 549 阅读 · 0 评论 -
redis原理4:redis核心数据结构
RedisDB主体数据结构String原创 2021-10-26 13:25:30 · 153 阅读 · 0 评论 -
常见数据结构排序算法时间复杂度
原创 2021-01-21 00:35:04 · 3140 阅读 · 2 评论 -
ConcurrentHashMap底层实现原理(JDK1.7 & 1.8)
前言我们都知道HashMap在多线程情况下,在put的时候,插入的元素超过了容量(由负载因子决定)的范围就会触发扩容操作,就是rehash,这个会重新将原数组的内容重新hash到新的扩容数组中,在多线程的环境下,存在同时其他的元素也在进行put操作,如果hash值相同,可能出现同时在同一数组下用链表表示,造成闭环,导致在get时会出现死循环,所以HashMap是线程不安全的。我们来了解另一个键值存储集合HashTable,它是线程安全的,它在所有涉及到多线程操作的都加上了synchronized关键转载 2020-12-31 00:02:42 · 338 阅读 · 0 评论 -
Java集合之NavigableMap与NavigableSet接口
本文接着上篇介绍SortedMap和SortedSet接口,介绍他们的扩展接口NavigableMap与NavigableSet接口,提供了针对给定搜索目标返回最接近匹配项的导航方法。SortedMap和SortedSet接口两个接口jdk1.2就已经提供,扩展的NavigableMap与NavigableSet接口jdk1.6才开始支持。1.NavigableSet接口 public interface NavigableSet<E> extends Sorted...转载 2020-10-13 15:41:02 · 369 阅读 · 0 评论 -
java枚举使用示例
/** * <p><b>Description:</b> 事件消费端枚举</p> * @author wangzhj * @date 2020年8月12日 */public enum ConsumerEnum { /** * 消息中间件 */ MQ("cis_mq"), /** * ESB */ ESB("esb_service"), .原创 2020-08-13 17:41:30 · 589 阅读 · 0 评论 -
mybatis分页插件com.github.pagehelper.PageHelper原理
在判断是否需要分页时,关键在于从ThreadLocal中取出分页信息,没有则表示无需分页。在PageHelper中的skip方法中判断:public class PageHelper extends PageMethod implements Dialect { private PageParams pageParams; private PageAutoDialect autoDialect; //判断是否需要分页 @Override public bool原创 2020-08-10 10:09:45 · 4001 阅读 · 0 评论 -
Java阻塞队列
本篇文章主要是介绍Java并发包中的几种阻塞队列和阻塞原理背景阻塞队列(BlockingQueue)是一个支持两个附加操作的队列。这两个附加的操作支持阻塞的插入和移除方法1)支持阻塞的插入方法:意思是当队列满时,队列会阻塞插入元素的线程,直到队列不满。2)支持阻塞的移除方法:意思是在队列为空时,获取元素的线程会等待队列变为非空阻塞队列常用于生产者和消费者的场景,生产者是向队列里添加元素的线程,消费者是从队列里取元素的线程。阻塞队列就是生产者用来存放元素、消费者用来获取元素的容器。.转载 2020-08-03 13:55:16 · 203 阅读 · 0 评论 -
Lambda表达式与递归
整数 n 的阶乘将所有小于或等于 n 的正整数相乘。 阶乘函数是一个常见的递归示例:// functional/IntCall.javainterface IntCall { int call(int arg);}// functional/RecursiveFactorial.javapublic class RecursiveFactorial { static IntCall fact; public static void main(String[] args) {原创 2020-07-28 18:15:25 · 642 阅读 · 0 评论 -
Java 的 Random 类的随机性
import java.util.*;public class Statistics { public static void main(String[] args) { Random rand = new Random(47); Map<Integer, Integer> m = new HashMap<>(); for(int i = 0; i < 10000; i++) { // Produce a number betwee.原创 2020-07-28 17:44:48 · 275 阅读 · 0 评论 -
dubbo中的LRU缓存
/* * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You u.原创 2020-07-28 15:43:32 · 362 阅读 · 0 评论 -
二叉树的前序遍历,中序遍历和后序遍历分别有什么作用
先序遍历:在第一次遍历到节点时就执行操作,一般只是想遍历执行操作(或输出结果)可选用先序遍历;中序遍历:对于二分搜索树,中序遍历的操作顺序(或输出结果顺序)是符合从小到大(或从大到小)顺序的,故要遍历输出排序好的结果需要使用中序遍历后序遍历:后续遍历的特点是执行操作时,肯定已经遍历过该节点的左右子节点,故适用于要进行破坏性操作的情况,比如删除所有节点作者:Entronad链接:https://ww...转载 2018-04-20 18:13:37 · 7795 阅读 · 4 评论 -
BTree和B+Tree详解
B+树索引是B+树在数据库中的一种实现,是最常见也是数据库中使用最为频繁的一种索引。B+树中的B代表平衡(balance),而不是二叉(binary),因为B+树是从最早的平衡二叉树演化而来的。在讲B+树之前必须先了解二叉查找树、平衡二叉树(AVLTree)和平衡多路查找树(B-Tree),B+树即由这些树逐步优化而来。二叉查找树二叉树具有以下性质:左子树的键值小于根的键值,右子树的键值大于根的键...转载 2018-04-21 11:36:13 · 6345 阅读 · 1 评论 -
一致性哈希算法
一直性Hash算法在很多场景下都有应用,尤其是在分布式缓存系统中,经常用其来进行缓存的访问的负载均衡,比如:redis等<k,v>非关系数据库作为缓存系统。我们首先来看一下采用取模方式进行缓存的问题。一致性Hash算法的使用场景 假设我们的将10台redis部署为我们的缓存系统,存储<k,v>数据,存储方式是:hash(k)%10,用来将数据分散到各个redis存储系统...转载 2018-05-04 10:42:34 · 133 阅读 · 0 评论 -
深入一致性哈希(Consistent Hashing)算法原理,并附100行代码实现
摘要: 本文为实现分布式任务调度系统中用到的一些关键技术点分享——Consistent Hashing算法原理和Java实现,以及效果测试。 本文为实现分布式任务调度系统中用到的一些关键技术点分享——Consistent Hashing算法原理和Java实现,以及效果测试。(代码实现见:https://github.com/yaohonv/pingpong/tree/master/c...转载 2018-05-04 10:47:50 · 172 阅读 · 0 评论 -
Java实现布隆过滤器
最近写爬虫需要降低内存的占用,现在用的是HashSet进行已爬URL的过滤,所以想到用布隆过滤器(Bloom Filter)来替换,从而减少内存的开销。因为HashSet内部是由HashMap处理的,HashMap则通过计算一个int型的hash值得出信息指纹,所以一个信息指纹占4字节,但是由于哈希的存储效率一般只有一半,所有说一条URL就需要8字节的信息指纹,而Bloom Filter 则只需要...转载 2018-06-06 15:35:07 · 722 阅读 · 0 评论 -
Java位运算原理及使用讲解
前言日常开发中位运算不是很常用,但是巧妙的使用位运算可以大量减少运行开销,优化算法。举个例子,翻转操作比较常见,比如初始值为1,操作一次变为0,再操作一次变为1。可能的做法是使用三木运算符,判断原始值为1还是0,如果是1,设置为0,否则设置为0.但是使用位运算,不用判断原始值,直接改变值就可以:1^num//num为原始值当然,一条语句可能对代码没什么影响,但是在高重复,大数据量的情况下将会节省很...转载 2018-06-07 14:03:33 · 534 阅读 · 0 评论 -
全局唯一id生成之雪花算法
雪花算法(Twitter_Snowflake)我们知道,分布式全局唯一id的生成,一般是以下几种:基于雪花算法生成基于数据库基于redis基于zookeeper本文说下雪花算法,后面附源码以及测试代码。如下图:如上图:雪花算法生成的id,总共64位第一位作为保留位,默认0中间41位用来存放时间戳,是当前时间与初始时间的差值,(1L << 41) / (100...转载 2019-05-22 18:46:42 · 7189 阅读 · 4 评论 -
BTree和B+Tree详解
B+树索引是B+树在数据库中的一种实现,是最常见也是数据库中使用最为频繁的一种索引。B+树中的B代表平衡(balance),而不是二叉(binary),因为B+树是从最早的平衡二叉树演化而来的。在讲B+树之前必须先了解二叉查找树、平衡二叉树(AVLTree)和平衡多路查找树(B-Tree),B+树即由这些树逐步优化而来。二叉查找树二叉树具有以下性质:左子树的键值小于根的键值,右子树的键值大...转载 2019-05-23 10:44:39 · 213 阅读 · 0 评论 -
java字节序、主机字节序和网络字节序
java程序员是幸福,因为相对于C/C++的不跨平台,JVM为我们屏蔽了大量的底层细节和复杂性,让我们能够将精力放在实现特定的业务逻辑上,所以使用java开发项目效率是比较高的。同时java程序员是悲哀的,就是因为JVM屏蔽了很多技术细节,导致java程序员基本功普遍较差,对一些基本概念理解不深,甚至根本没有听说过。作为一个java程序员,我深深的感到自己知识面的狭窄。无意中看到了字节序,以前竟...转载 2019-05-27 20:09:34 · 678 阅读 · 0 评论 -
异或运算
异或运算,把数转换为二进制以后进行异或运算,相同为0不同为1publicstaticvoidmain(String[]args){inta=10;//转化为二进制是(1010)intb=5;//转化为二进制是(0101)System.out.println(a^b);//异或后对应二进制:1111——>15}...原创 2019-07-19 10:08:33 · 611 阅读 · 0 评论 -
Hashmap自身的hashCode()方法和equals()方法
如果以一个HashMap作为一个Map的key,就需要用到HashMap自身的hashCode()方法和equals()方法了,的hashCode方法继承自AbstractMap源码如下:public int hashCode() { int h = 0; Iterator<Entry<K,V>> i = entrySet().it...原创 2019-07-19 10:34:48 · 622 阅读 · 0 评论 -
用java实现七种排序算法
一、文章编写风格总览 选择排序、插入排序、冒泡排序、归并排序、快速排序、希尔排序、堆排序、 最后对各种排序算法进行比较,理清楚各种排序的优缺点。 其中快速排序是冒泡排序的增强,堆排序是对选择排序的增强,希尔排序是对插入排序的增强,这就6种了,最后一种就是归并排序。 二、选择排序 选择排序是我认为最简单的一种排序了,因为我们自己也很容易想到这种方法对数组...转载 2018-04-19 11:45:18 · 267 阅读 · 0 评论