- 博客(42)
- 收藏
- 关注
原创 Fabric
1 安装Go、docker、docker-compose1.1 安装Go获取go的安装包并解压到/usr/local文件夹下:sudo wget -P /usr/local https://studygolang.com/dl/golang/go1.15.linux-amd64.tar.gzcd /usr/localsudo tar -zxvf go1.15.linux-amd64.tar.gz添加环境变量vim ~/.bashrc将一下内容插入bashrc中export GOROOT
2022-04-01 11:59:48 8357
原创 Redis相关面经
分布式锁为什么使用分布式锁随着业务发展的需要,原单体单机部署的系统被演化成分布式集群系统后,由于分布式系统多线程、多进程并且分布在不同机器上,这将使原单机部署情况下的并发控制锁策略失效,单纯的Java API并不能提供分布式锁的能力。为了解决这个问题就需要一种跨JVM的互斥机制来控制共享资源的访问,这就是分布式锁要解决的问题!也就是说,相同的服务部署到不同的服务器上,如何保证相同的共享变量的一致性,即保证在同一时刻只能由一台服务器中的共享变量被一条线程修改。如线程1对jvm1中的变量A修改,如果没有
2021-08-06 15:26:11 176
原创 MVCC实现
MVCC基本思想通过mvcc解决读未提交、不可重复读的问题,但是要解决幻读,则需要加锁解决(next-key-locks)MVCC是乐观锁的一种实现,是通过保存数据在某一个时间点的快照实现的,写操作更新最新的版本(写操作是要加锁的),读操作读取旧版本。MVCC是实现隔离级别的一种机制,用于实现读取已提交和可重复读这两种隔离级别(MVCC单单解决的是可重复读,没有解决幻读)。大多数事务型存储引擎实现都不是简单的行锁,基于并发性的考虑,一般会同时实现多版本并发控制(MVCC)处理读写冲突。MVCC
2021-08-06 15:24:39 372
原创 LinkedHashMap&TreeMap
LinkedHashMap的特性链接: link.可以按照put的顺序读取存储的元素。LinkedHashMap结构LinkedHashMap继承于HashMap,即所有的节点还是存储到HashMap中,但是与HashMap中的Node节点不同的是,LinkedHashMap中的Entry节点继承于HashMap中的Node节点,而且还新增了Entry before和Entry after,这两个指针。这样LinkedHashMap中所有的节点构成了一个双向的链表。同时在LinkedhashMap中
2021-04-08 13:24:49 360
原创 String&StringBuffer&StringBuilder
Stringpublic final class String //被final修饰,不能被继承 implements java.io.Serializable, Comparable<String>, CharSequence{ /** The value is used for character storage. */ private final char value[];//维护了一个字符数组,用来存储字符,且用final修饰 /** The o
2021-04-08 10:33:58 88
原创 计网&操作系统面经相关
TCP第三次握手的必要性见韩计网word客户端发送的第一个 syn 包丢包会发生什么 || 服务端发送的 syn/ack 包丢包tcp 和 udp 分别适用于什么场景UDP特点(首部占8字节)(1)面向无连接的(2)不可靠传输,知识尽最大努力交付(3)面向数据报(即不对数据分段,把应用层传下来的数据报加上UDP头部直接发送送给网络层)UDP使用场景当对网络通讯质量要求不高的时候,要求网络通讯速度能尽量的快,这时就可以使用UDP。常见使用UDP协议的应用如下:QQ语音,QQ视频,TFTP等
2021-04-01 20:43:33 171
原创 框架相关面经
AOP面向对象编程(OOP)解决问题的重点在于对具体领域模型的抽象,而面向切面编程(AOP)解决问题的关键则在于对关注点的抽象。也就是说,系统中对于一些需要分散在多个不相关的模块中解决的共同问题,则交由AOP来解决;AOP能够使用一种更好的方式来解决OOP不能很好解决的横切关注点问题以及相关的设计难题来实现松散耦合。Spring事务链接: link.链接: link.(1)spring声明式事务的实现就是通过环绕增强的方式,在目标方法执行之前开启事务,在目标方法执行之后提交或者回滚事务,事务拦截器的
2021-04-01 20:43:23 194
原创 数据库面经相关
数据库表设计过程链接: 参考.如果不进行范式,可能出现:如一个关系模式包含User(用户ID,用户密码,用户名,购买的商品名,购买的商品价格)(1)数据大量冗余。当每次购买商品时都要添加用户信息。(2)删除异常。当删除商品购买记录时,要把用户信息删除。(3)添加异常:添加用户时,商品信息必须是空。(4)更新异常:值更新用户信息时,要考虑保留商品信息不变。应用举例需求:假设我们现在需要设计一个小型电商平台的数据库,包含:用户名字,用户电话,商品价格,商品名字等属性。第一步:那么我们就先建
2021-04-01 20:40:39 134
原创 JVM面经相关
JVM为什么要指令重排序有数据依赖的两条指令静止重排序指令重排序有两类,编译器重排序和处理器重排序。编译器重排序发生在编译期,处理器重排序发生在运行时。其实指令重排序的本意是提高程序并发效率,原则是重排序后的程序运行结果和单线程运行结果一致。...
2021-03-31 16:56:05 139
原创 多线程面经相关
如何理解线程与进程之间的关系线程:进程是系统调度的基本单位,一个进程至少拥有一个线程,这些线程共享进程的地址空间,线程是进程中实际运作的单位。进程:进程是运行的程序,是系统进行资源分配的基本单位即每个进程拥有自己的地址空间。**进程与线程的关系:**一个进程至少包含一个线程,所有的线程共享进程的地址空间(资源)。进程与线程区别:线程的状态(java中)NEW(初始状态):线程对象已经被创建,已经分配了资源,但是没有调用start方法。RUNNABLE(运行状态):该状态下包含就绪和运行状态。
2021-03-31 16:55:49 115
原创 一致性Hash算法
在分布式集群中,对机器的添加删除,或者机器故障后自动脱离集群这些操作是分布式集群管理最基本的功能。如果采用常用的服务器IP = hash(object)%服务器数量(N为可以处理请求的主机个数)算法,那么在有机器添加或者删除后,很多原有的数据就无法找到了,这样严重的违反了单调性原则。设计的目标是:在服务器数量变动的情况下(1)尽量提高缓存的命中率(2)缓存数量尽量平均分配。为了解决服务器数量变化带来的大量对象存储位置失效,可以采用一致性Hash算法。一致性Hash算法一致性哈希解决的本质问题是:相同
2021-03-30 18:07:40 112
原创 布隆过滤器
布隆过滤器使用场景例如如下问题:(1)字处理软件中,需要检查一个英语单词是否拼写正确(2)在 FBI,一个嫌疑人的名字是否已经在嫌疑名单上(3)在网络爬虫里,一个网址是否被访问过(4)yahoo, gmail等邮箱垃圾邮件过滤功能以上这些场景有个共同的问题:如何查看一个东西是否在有大量数据的池子里面。布隆过滤器原理布隆过滤器包含一个超大的位数组 以及 k个hash函数(每个hash函数的作用就是将元素映射到位数组的一个位置上)总体思路是,向过滤器中添加元素时,就是通过k个不同的hash函数
2021-03-30 15:55:28 72
原创 面经汇总
线程池讲讲线程池的实现原理(1)如果当前线程池中工作线程数量小于corePoolSize,那么直接执行addWorker方法,将当前任务(即Runnable)构建为工作线程,并执行该任务。(要获取全局锁:ReentrentLook)。(2)如果当前线程池中工作线程数量>=corePoolSize,那么执行blockingqueue.offer方法,把当前任务放入阻塞队列中,如果加入队列成功后还要检测当前线程池如果已经停止,则直接从队列移除该任务,如果线程池中没有工作线程,则调用addWorke
2021-03-28 20:51:28 233
原创 ArrayList
成员变量private static final int DEFAULT_CAPACITY = 10; //如果在new一个ArrayList时没有指定容量,则默认大小为10transient Object[] elementData; // 数组,用于存储元素,即ArrayList是用数组实现private int size; //当前Object[] 数组中元素个数(注意不是数组大小)private static final Object[] EMPTY_ELEMENTDATA = {
2021-03-28 19:13:08 130
原创 集群
集群中的数据结构在clusterState中保存了一个跳跃表。用来保存该节点中槽(socre)与键(member)之间的关系,跳跃表中节点以score排序。优点:节点可以方便对属于某个和某些槽的所有数据库键进行批量操作。...
2021-03-23 15:37:11 103
原创 Sentinel(哨兵)
Sentinel本质上是一个运行在特殊模式下的Redis服务器。其可以监视任意多个主服务器,以及这些主服务器的所有从服务器;当主服务器下线时,自动将从服务器升级为新的主服务器,新的主服务器代替下线服务器继续就收命令请求。Sentinel模式下关键数据结构从上面结构可知:sentinel服务器中的Sentinel状态中包含了该sentinel监视的所有主服务器实例(即通过dict *master)。在主服务器实例中,又包含着该主服务器所有从服务器实例(dict *slaves)以及监视该主服务的所有se
2021-03-21 17:13:57 124
原创 复制
Redis复制功能分为两个操作:(1)同步(先):将从服务器状态更新至与主服务器当前状态一致。(2)命令传播(后):将主服务器执行的写指令,发送给从服务器。当一个服务器,要作为另外一个服务器的从服务器时,需要执行slave of ip:port(主服务器的ip:port)。旧版本同步的实现同步过程如下:(1)从服务器向主服务器发送SYNC指令(2)主服务器收到SYNC指令后,执行BGSAVE指令,生成RDB文件,同时使用一个缓冲区记录现在开始执行的所有写指令。(也就是说bgsave时服务器接
2021-03-21 12:00:29 150
原创 事件
IO 多路复用详细见: link.redis默认使用epoll多路复用函数库。IO多路复用理解:每一个网络连接都对应一个文件描述符(fd),高效的网络服务器都可以供多个客户端同时连接即产生多个文件描述符,然后单线程不断的去轮询这些描述符,如果有消息就处理。大致代码如下:while(true){ for(fdx in fdA -fdE){ if(fdx有数据) 读取fdx,处理数据; }}select IO多路复用(1)首先将需要被监听的文件描述符放入数组中—fds[],数组中.
2021-03-20 19:09:13 144
原创 Redis持久化
RDB持久化rdb持久化是将Redis在内存中某一时刻数据库状态(每个数据库中的键值对)保存到磁盘中。RDB文件创建SAVE指令redis > SAVE //执行SAVE指令时,服务器进程会阻塞,直到RDB文件创建OKdef SAVE: rdbSave() //主线程执行rdbSave()函数来创建rdb文件,会阻塞Redis服务器进程,服务器不处理任何请求。BGSAVE指令redis>BGSAVE //会派生一个子进程来创建rdb文件,主进
2021-03-20 16:55:58 78
原创 设置键的生存时间、过期时间以及过期删除策略
设置生存时间和过期时间设置生存时间----即让键在指定秒数或毫秒数之后过期expire key ttl---- expire key 5;即让键在5s后过期pexpire key ttl ---- pexpire key 6;即让键在6ms之后过期设置过期时间—即让键在某一时刻过期expireat key timstamp — expire key 1377257300;让键在1377257300这个时刻过期pexpireat key timestamp ;以毫秒为单位。(前三个指令都
2021-03-20 12:03:43 485
原创 静态代理&动态代理
代理是一种模式,提供了对目标对象的间接访问方式,即通过代理访问目标对象。如此便于在目标实现的基础上增加额外的功能操作,前拦截,后拦截等,以满足自身的业务需求。静态代理(1)实现方式:编写一个代理类,实现与目标对象相同的接口,并在代理类内部维护一个目标对象的引用,该目标对象通过构造器传入。在代理对象中调用目标对象相同的方法,并添加前拦截器,后拦截器等业务功能动态代理动态代理中所谓的动态,是针对使用java代码实际编写代理类的“静态”而言,它的优势不在于省去了编写代理类那一点工作量(直接获得一个代理对
2021-03-18 16:01:41 58
原创 ThreadPoolExecutor#execute源码分析
线程池的整体处理流程如下(1)如果当前线程池中工作线程数量小于corePoolSize,那么直接执行addWorker方法,将当前任务(即Runnable)构建为工作线程,并执行该任务。(要获取全局锁:ReentrentLook)。(2)如果当前线程池中工作线程数量>=corePoolSize,那么执行blockingqueue.offer方法,把当前任务放入阻塞队列中。(3)如果offer方法返回false,即队列已满则执行addWorker方法,构建工作线程,执行该任务。(4)但是如果当前
2021-03-09 17:27:26 80
原创 Java与线程
java与线程java提供了在不同硬件和操作系统环境下对线程操作的统一处理,每个已经通过start()方法且还没结束的java.lang.Thread类的实例就代表一个线程。线程实现方式使用内核线程实现(1:1实现)内核线程(KLT,即操作系统原生线程)定义:直接由操作系统内核支持的线程,操作系统内核负责内核线程的切换,内核通过操控调度器对线程进行调度,并负责将** 线程的任务映射**到各个处理器上。内核线程提供一种高级接口–轻量级进程(LWP–给应用程序使用,每个轻量级进程都由一个内核线
2020-10-26 20:19:04 119
原创 java内存模型
java内存模型定义java内存模型可以屏蔽各种硬件和操作系统的内存访问差异,实现让java程序在各个平台能够达成一致的内存访问效果。java内存模型的目的是:定义程序中各个变量的访问规则(即把变量值存储到内存以及从内存中取出这样的底层细节)。注这里的变量为实例变量、静态变量还有构成数组对象的元素。不包括方法中定义的变量,以为方法最终转化为栈帧,放到虚拟机栈中,是线程私有的,不存在共享。主内存和工作内存主内存作用(可以视为硬件中的主存,主内存是虚拟机内存的一部分):所有变量都存储在主内存中,不
2020-10-25 10:24:58 77
原创 学习笔记1
Monitor(1)synchronized的底层就是通过Monitor实现的,monitor是实现java线程互斥与协作的手段,可以将monitor视为对象或者Class的锁,每个对象都有唯一一个monitor.(2)下图是线程与monitor之间的关系,以及线程的状态转换:什么时候线程在Entry Set:线程通过synchronized获取对象锁(monitor),但是对象锁被其他线程拥有,此时该线程进入entry set;否则线程拥有锁,执行临界区代码(被synchronized保护的代码为临
2020-10-11 17:27:34 102
原创 虚拟机类加载机制
类加载机制定义: 虚拟机把描述类的数据从Class文件加载到内存,并堆数据进行校验、转换解析和初始化,最终形成被虚拟机直接使用的java类型。类型的加载、连接和初始化过程都是在程序运行期间完成,java动态扩展的特性就是依赖运行期间动态加载和动态连接这个特点实现的。如:编写一个面向接口的应用程序,可以等到运行时再指定其实际的实现类。类加载时机类加载过程(1)加载(2)验证(3)准备(4)解析(5)初始化类加载器...
2020-09-28 14:37:22 125
原创 JVM OOP-Klass二分模型
1 概述HotSpot是基于c++实现,而c++是一门面向对象的语言,本身具备面向对象基本特征,所以Java中的对象表示,最简单的做法是为每个Java类生成一个c++类与之对应。但HotSpot JVM并没有这么做,而是设计了一个OOP-Klass Model。这里的 OOP 指的是 Ordinary Object Pointer (普通对象指针),它用来表示对象的实例信息,看起来像个指针实际上是藏在指针里的对象。而 Klass 则包含元数据和方法信息,用来描述Java类。之所以采用这个模型是因为Ho
2020-09-26 20:47:27 685
原创 类文件结构描述
java语言平台无关性java语言为什么平台无关:虚拟机运行在不同的平台上,但是这些虚拟机都可以加载和执行字节码文件,这样字节码文件就可以在不同的平台上执行。(即:虚拟机是与平台相关的,但是字节码文件是与与平台无关)。Class类文件结构(构成)class文件特点:(1)一组以8个字节为基础单位的二进制流,各个数据项目紧凑排列在文件之中,没有任何分隔符。(2)文件中只有两种数据类型:无符号数和表无符号数:属于基本的数据类型,u1,u2,u4,u8分别表示1、2、4、8字节的无符号数。无符号数
2020-09-25 11:18:29 308
原创 voliate关键字原理
被volatile修饰的变量在编译成字节码文件时会多个lock指令,该指令在执行过程中会生成相应的内存屏障,以此来解决可见性跟重排序的问题。voliate关键字作用静止重排序保证变量赋值操作的顺序与程序代码中的执行顺序一致。线程可见性原理使用场景...
2020-09-25 11:17:31 17212 2
原创 虚拟机性能监控、故障处理工具
jps:虚拟机进程状况工具jps -l: 显示虚拟机运行的进程ID 和 执行的主类(Mian()函数所在的类)jps -v:显示虚拟机启动时被设置的参数jps -q:值显示进程ID,不显示主类信息jstat:虚拟机统计信息监视工具jstat命令格式:jstat [ option vmid [ interval[s|ms] [count]]]其中vmid是虚拟机进程id 。interval和count为查询间隔和次数,如果省略这个参数表示查询一次。比如:jstat -
2020-09-24 09:20:07 129
原创 java虚拟机--选择合适的收集器、内存分配与回收策略实战
垃圾收集器的作用:垃圾收集器除了垃圾收集之外,还负责堆的管理与布局、对象分配、与解释器协作、与编译器协作、与监控子系统协作等Epsilon垃圾收集器特点:不进行垃圾收集,只进行对象的分配。应用场景:如果应用只运行几分钟或者几秒钟,在堆耗尽之前就会退出,那么只需要垃圾收集器能够为对象分配内存即可,不用涉及垃圾收集,这是不进行垃圾回收的Epsilon垃圾收集器很有用。垃圾收集器的权衡指标应用程序关注点:应用进行数据分析、计算等,需要高吞吐量?应用需要与用交互,需要低延迟?是客户端应用或者嵌入.
2020-09-18 15:38:19 155
原创 java虚拟机--低延迟垃圾收集器(ZGC收集器)
ZGC(Z Garbage Collector)是一款在JDK11中新加入的具有实验性质的低延迟垃圾收集器ZGC特征ZGC基于Region的内存布局,(暂时)不设分代,使用读屏障、染色指针和内存多重映射等技术来实现可并发的标记-整理算法,以低延迟为首要目标的一款垃圾收集器读屏障理解:这与其他GC使用的写屏障形成对比,例如G1。读屏障的工作是检查引用的状态,并在将引用(或者甚至是不同的引用)返回给应用程序之前执行一些工作。 在ZGC中,它通过测试加载的引用来执行此任务,以查看是否设置了某些位。 如果.
2020-09-17 19:30:34 224
原创 java虚拟机--低延迟垃圾收集器(Shenandoah收集器)
Shenandoah收集器是由RedHat公司开发的项目,Oracle拒绝在OracleJDK12中支持该收集器,Shenandoah只有在OpenJDK中才会包含,而OracleJDK中不包含的。该收集器的目标:无论堆的大小如何,都可以把垃圾收集器的停顿时间限制在10ms以内。Shenandoah工作过程(1)初始标记标记GC Roots直接引用的对象。需要stop the world,时间长度取决于GC Roots的多少。(2)并发标记从GC Roots直接引用的对象出发,进行可达性.
2020-09-16 15:12:45 436
原创 java虚拟机--经典垃圾收集器
图中展示了其中作用于不同分代的收集器,如果两个收集器之间存在连线,就说明它们可以搭配使用,图中收集器所处的区域,则表示它是属于新生代收集器还是老年代收集器Serial收集器(新生代)该收集器是一个单线程工作的收集器,不仅仅使用一条垃圾收集线程完成垃圾收集工作,而且该垃圾收集器进行垃圾收集工作(标记-复制)时,必须暂停其他所有工作的线程(Stop The World),直到垃圾收集结束。Serial/Serial Old垃圾收集器运行示意图无论是标记-复制还是标记-整理垃圾算法,标记过程都是一样的.
2020-09-13 20:34:01 215
原创 java虚拟机--对象死亡判定、垃圾收集算法、HotSpot的算法细节实现
对象已死?判断对象是否已死(可以被回收)的方法引用计数法实现方式:为每个对象添加一个引用计数器,当一个地方引用了该对象,计数器加1,当引用失效,计数器减法1,,计数器减为0是,该对象就可以被清理。存在的问题:难以解决对象的循环引用。故java虚拟机中没有使用引用计数器来管理内存。可达性分析法java虚拟机通过可达性分析判定对象是否存活。实现过程:从GC Roots开始,根据引用关系搜索(搜索所走的路径成为引用链),如果GC Roots到某个对象不可达,那么说明该对象以不被使用。
2020-09-08 17:20:50 213
原创 java内存管理--OutOfMemoryError(内存溢出异常)
java堆溢出可以通过-Xms 20m -Xmx 20m来设置堆的最小与最大内存。通过参数-XX:+HeapDumpOnOutOfMemoryError参数,当堆中发生内存溢出异常时,生成内存快照。堆内存溢出是最常见的异常。解决该异常首先要对发生异常时候的内存快照进行分析,第一步是确认导致内存溢出的对象是不是有必要的(即分清楚是内存泄露(Memory Leak,即无用的对象占用内存不释放内存)还是内存溢出(Memory Overflow))。如果是内存泄露,通过工具查看泄露对象到GC roots的引
2020-09-05 19:10:25 266
原创 Java内存管理--对象
对象创建过程判定类是否被加载、解析初始化。虚拟机遇到new指令,首先检查这个指令的参数是否能在运行时常量池中定位到符号应用,并且检查该符号引用代表的类是否被加载、解析、初始化过。如果没有则进行类加载。为对象分配内存。在java堆中划分出一块确定大小的内存,该内存的大小在类加载阶段就已经确定。分配内存的方式指针碰撞当堆中使用的Serial、ParNew等带压缩整理的垃圾收集器时,java堆中的内存是规整的(使用过的内存与空闲内存完全分开,中间放一个指针),当分配内存时,仅仅是将指针向空闲内存
2020-09-05 15:48:52 184
原创 Java内存管理--运行时数据区
运行时数据区java虚拟机在执行java程序的时候,把管理的内存划分为若干个不同的数据区域,不同区域的用途、创建时间、销毁时间不同java虚拟机把管理的内存(运行时数据区)划分为一下几个部分程序计数器java虚拟机栈本地方法栈方法区堆程序计数器程序计数器是是一块较小的内存,可以看作当前线程所执行的字节码行号指示器。如果线程执行的是一个java方法,那么计数器记录的是该线程正在执行的字节码指令地址。如果正在执行的是一个本地方法,该计数器的值为空。为了线程切换后能恢复到正确的执行
2020-09-05 10:28:03 172
原创 反序数【数位拆解】(九度1064)
题目描述:设N是一个四位数,它的9倍恰好是其反序数(例如:1234的反序数是4321)求N的值输入:程序无任何输入数据输出:输出题目要求的四位数,如果结果有多组,则每组结果之间以回车隔开思路从1000循环到2000(2000*9必定为5为数),每循环一次直接计算该数的反序数与原数比较代码:#include &lt;stdio.h&gt;int main() { for(in...
2019-01-08 20:35:28 1139
空空如也
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人