HashMap底层红黑树与MySQL索引

前置知识:什么是时间复杂度?如何计算时间复杂度?

常见的时间复杂度及关系:O(1)<O(logn)<O(n)<O(n^2)
以吃面包为例,问吃面包需要的时间:
O(1):一口吃一个面包,时间最短。
O(logn):一口吃掉面包的一半,时间比较短。
O(n):一口吃掉面包的一寸,时间比较长。
O(n^2):一口吃掉面包的一寸,第二口开始减半,吃半寸,第三口吃四分之一寸……时间最长。

详见一套图搞懂时间复杂度

前置知识:常见的查找算法有哪些?

遍历:暴力 for 时间复杂度O(n)
二分法(二叉搜索树/二叉查找树):能做二分查找必须是有序的 O(logn)
哈希:最高效。 O(1) JDK1.8里面HashMap:链表+红黑树,几种算法的组合拳。
索引:搜索引擎
bfs&dfs:图论里面的遍历
平衡树
B+树
B-Tree
红黑树:高效的查找算法。

哈希

Hash也译作散列,是一种将任意长度的消息压缩到某一固定长度的消息摘要的函数。
哈希可以有多种算法进行实现。
优秀的哈希算法可以让输出很均匀地散列在值域。

哈希算法是无法逆向推导的。

HashMap为什么查找快?

因为通过对key取哈希可以很快得到hashcode,从而得到存放位置,进而得到指针(内存地址),最终就快速找到了内容value。

二分法/ 二叉搜索树/二叉查找树

数据必须有序才可使用。猜大小游戏。时间复杂度为O(logn)。极端情况会成为链表,时间复杂度O(n)。

红黑树

特殊的二叉查找树,通过左旋或右旋实现自动平衡,避免链表化。

索引

能作为数据库索引的数据结构有哪些?

数组(不适合大数据量),链表(不适合大数据量)。

Hash(不能范围查找)

红黑树(数据库是存磁盘的,树太高,树的每一层都读一次,读磁盘次数太多。磁盘上一页能存16kb数据,读一次16kb,只取一个4字节的int,非常浪费。)

所以数据库MySQL中采用的可以:

B树(就是B-Tree),B+树

B树

n叉的排序树。

B+树

HashMap底层

JDK中常见的集合容器包括哪些?

主要有List Set和Map三个接口以及实现了这些接口的诸多子类。

List Set是实现了Collection接口,Map是单独的接口。

List Set Map在概念上的差别?

List是有序的,元素可重复;
Set是无序的,元素不可重复;(最多只能有一个元素为null)
Map是无序的,存储的元素为Entry键值对,其中键不可重复。(最多只能有一个键值为null)

HashMap数据结构

HashMap在底层维护了一个长度为16的数组(名为table),里面存放的是Entry(Entry是接口,Node是实现)对象,也就是键值对。在存放时需要先把key进行hash运算,得到hashcode,用hashcode对数组长度进行取模得到的数字作为该Entry对象在数组中的位置。

优秀的hash算法可以使元素均匀地分布于数组中。如果HashMap底层数组中每个位置最多只有一个元素,则查找元素的时间复杂度为O(1)。

当出现n个元素的位置相同时,这n个元素都会形成一个链表挂载到数组的某位置。查找的时间复杂度O(n)。

JDK1.8对此进行了优化,如果挂载的链表太长,超过8个,就会将这个链表转化成红黑树。查找元素的时间复杂度O(logn)。这样就起到了一定的优化作用。

为什么这个长度设置为8呢?和泊松分布有关,是类库的设计者在时间和空间开销上作的取舍。

loadFactor负载因子默认为0.75,当数组table的格子被占用达到16*0.75=12个的时候进行2倍扩容。(简单理解)

tip:transient修饰符修饰的属性是不会被序列化的。序列化、反序列化之后是不可见的。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值