0%

布隆过滤器 Bloom Filter

大概的思路就是,当你请求的信息来的时候,先检查一下你查询的数据我这有没有,有的话将请求压给数据库,没有的话直接返回

  • 存入过程

    通过三个hash函数计算出三个哈希值,然后将三个值映射到数组中将0改成1。

  • 查询过程

    通过三个hash函数计算出查询数据的哈希值,然后检查布隆过滤器对应位置上的值是否为1,如果有一个不为1表示该值不存在,如果都为1表示该值可能存在。(查询时间复杂度为O(k),k为哈希函数个数)

  • 删除过程

    不能进行删除,因为会删除掉其他数据。

  • 更新过程

    不能进行更新。

原理

布隆过滤器基础版

原理就是一个对一个key进行k个hash算法获取k个值,在比特数组中将这k个值散列后设定为1,然后查的时候如果特定的这几个位置都为1,那么布隆过滤器判断该key存在。

一个bitmap用于记录,bitmap原始数值全都是0。当一个数据存进来的时候,用三个Hash函数分别计算三次Hash值,并且将bitmap对应的位置设置为1,上图中,bitmap 的1,3,6位置被标记为1,这时候如果一个数据请求过来,依然用之前的三个Hash函数计算Hash值,如果是同一个数据的话,势必依旧是映射到1,3,6位,那么就可以判断这个数据之前存储过,如果新的数据映射的三个位置,有一个匹配不上,假如映射到1,3,7位,由于7位是0,也就是这个数据之前并没有加入进数据库,所以直接返回。

Redis的bitmap只支持2^32大小,对应到内存也就是512MB,误判率万分之一,可以放下2亿左右的数据,性能高,空间占用率及小,省去了大量无效的数据库连接。

阅读全文 »

Spring 容器是什么

Spring容器帮程序员处理了大量繁琐的过程,可以说Spring 容器是 Spring 框架的核心。

Spring容器到底是什么

从概念上讲

Spring 容器是 Spring 框架的核心,是用来管理对象的。容器将创建对象,把它们连接在一起,配置它们,并管理他们的整个生命周期从创建到销毁。

从具象化讲

在java项目中,我们使用实现了org.springframework.context.ApplicationContext接口的实现类。在web项目中,我们使用spring.xml——Spring的配置文件。

从代码上讲

一个Spring容器就是某个实现了ApplicationContext接口的类的实例。也就是说,从代码层面,Spring容器其实就是一个ApplicationContext(一个实例化对象)。

阅读全文 »

ElasticSearch

简介

Elasticsearch(简称ES)是一个分布式、可扩展、实时的搜索与数据分析引擎。ES不仅仅只是全文搜索,还支持结构化搜索、数据分析、复杂的语言处理、地理位置和对象间关联关系等。

ES的底层依赖Lucene,Lucene可以说是当下最先进、高性能、全功能的搜索引擎库。但是Lucene仅仅只是一个库。为了充分发挥其功能,你需要使用Java并将Lucene直接集成到应用程序中。更糟糕的是,您可能需要获得信息检索学位才能了解其工作原理,因为Lucene非常复杂——《ElasticSearch官方权威指南》。

鉴于Lucene如此强大却难以上手的特点,诞生了ES。ES也是使用Java编写的,它的内部使用Lucene做索引与搜索,它的目的是隐藏Lucene的复杂性,取而代之的提供一套简单一致的RESTful API。

总体来说,ES具有如下特点:

  • 一个分布式的实时文档存储引擎,每个字段都可以被索引与搜索
  • 一个分布式实时分析搜索引擎,支持各种查询和聚合操作
  • 能胜任上百个服务节点的扩展,并可以支持PB级别的结构化或者非结构化数据
阅读全文 »

Lock

公平和非公平锁

公平锁指的就是:在竞争环境下,先到临界区的线程比后到的线程一定更快地获取得到锁

那非公平就很好理解了:先到临界区的线程未必比后到的线程更快地获取得到锁

怎么实现公平和非公平锁?

公平锁可以把竞争的线程放在一个先进先出的队列上

只要持有锁的线程执行完了,唤醒队列的下一个线程去获取锁就好了

非公平锁的概念上面已经提到了:后到的线程可能比前到临界区的线程获取得到锁

那实现也很简单,线程先尝试能不能获取得到锁,如果获取得到锁了就执行同步代码了

如果获取不到锁,那就再把这个线程放到队列呗

所以公平和非公平的区别就是:线程执行同步代码块时,是否会去尝试获取锁。

如果会尝试获取锁,那就是非公平的。如果不会尝试获取锁,直接进队列,再等待唤醒,那就是公平的。

阅读全文 »

Spring 三级缓存

Spring的三级缓存解决循环依赖问题

  • org.springframework.beans.factory.support.DefaultSingletonBeanRegistry

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    /**
    * 一级缓存,用于存放完全初始化好的 bean,从该缓存中取出的 bean 可以直接使用
    *
    * Cache of singleton objects: bean name to bean instance.
    */
    private final Map<String, Object> singletonObjects = new ConcurrentHashMap<>(256);

    /**
    * 二级缓存,提前曝光的单例对象的cache,存放原始的 bean 对象(尚未填充属性),用于解决循环依赖
    *
    * Cache of early singleton objects: bean name to bean instance.
    */
    private final Map<String, Object> earlySingletonObjects = new ConcurrentHashMap<>(16);

    /**
    * 三级缓存,单例对象工厂的cache,存放 Bean 工厂对象,用于 解决 循环依赖、代理类问题
    *
    * Cache of singleton factories: bean name to ObjectFactory.
    */
    private final Map<String, ObjectFactory<?>> singletonFactories = new HashMap<>(16);


    /**
    * bean被创建完成之后,注册
    * Set of registered singletons, containing the bean names in registration order.
    */
    private final Set<String> registeredSingletons = new LinkedHashSet<>(256);

    /**
    * 正在创建过程中的bean待的地儿,bean在开始创建的时候放入,直到创建完成将其移除
    * Names of beans that are currently in creation.
    */
    private final Set<String> singletonsCurrentlyInCreation =
    Collections.newSetFromMap(new ConcurrentHashMap<>(16));
  • SpringBoot 依赖注入方式

    • 基于字段 @Filed 的依赖注入

      支持解决循环依赖(Spring 5后不建议使用)

    • Setter 方法注入

      支持解决循环依赖

    • 构造器注入

      流程: 获取构造器,将参数传入构造器后进行反射生成Instance。但如果此时构造器中的参数为Null,此刻无法正常创建Bean。

      因此不支持解决循环依赖

阅读全文 »

SpringBoot 生命周期

SpringBoot应用的生命周期,整体上可以分为SpringApplication初始化阶段、SpringApplication运行阶段、SpringApplication结束阶段、SpringBoot应用退出四个阶段。

阅读全文 »

Tomcat-为什么要JAVA破坏双亲委派机制

简述

  • Tomcat本身也是一个Web应用程序
  • 不同Web程序依赖不同,向上查询时可能导致依赖版本异常

打破双亲的机制,每个应用独立classloader其实自己做到隔离机制

阅读全文 »

1.String是字符串常量,用final修饰,StringBuffer和StringBuilder是字符串变量

2.StringBuffer中的方法都是用Synchrionzed修饰的,所以线程是安全的,StringBuilder不保证线程安全

3.运行速度上StringBuilder>StringBuffer>String

因为String对象是一个不断创建新对象不断回收的过程