自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(67)
  • 收藏
  • 关注

原创 锁 synchronized和lock

当方法调用时, 调用指 令将会 检查方法的 ACC_SYNCHRONIZED 访问标志是否被设置, 如果设置了, 执行线 程将先持有 monitor (虚拟机规范中用的是管程一词), 然后再执行方法, 最后再方 法完成(无论是正常完成还是非正常完成)时释放 monitor。当锁计数器为 0 时, 该锁就被释放 了。1.Lock 的加锁和解锁都是由 java 代码配合 native 方法 (调用操作系统的相关方 法) 实现的, 而 synchronize 的加锁和解锁的过程是由 JVM 管理的。

2024-04-25 12:39:34 188

原创 Atomic类

UnSafe 类的 objectFieldOffset() 方法是个本地方法, 这个方法是用来拿“原值”的 内存地址, 返回值是 valueOffset;另外, value 是一个 volatile 变量, 因此 JVM 总是可以保证任意时刻的任何线程总能拿到该变量的最新值。CAS 的原理, 是拿期望值和原本的值作比较, 如果相同, 则更新成新的值。

2024-04-25 12:37:12 116

原创 ClassNotFoundException NoClassDefFoundError 异常的区别以及产生的原因

ClassNotFoundException和NoClassDefFoundError都表示类没有被找到,但它们的原因不同。ClassNotFoundException表示Java虚拟机在运行时找不到某个类,而NoClassDefFoundError表示Java虚拟机在运行时找到了某个类的定义文件,但无法正确地加载它。

2024-04-25 12:22:16 35

原创 sleep和wait的区别

sleep是Thread的静态类方法,谁调用的谁去睡觉,即使在a线程里调用了b的sleep方法,实际上还是a去睡觉,要让b线程睡觉要在b的代码中调用sleep。4、sleep必须捕获异常throws InterruptedException,而wait,notify和notifyAll不需要捕获异常。3、使用范围:wait,notify和notifyAll只能在同步控制方法或者同步控制块里面使用,而sleep可以在任何地方使用。1、sleep来自Thread类,和wait来自Object类。

2024-04-25 12:02:28 102

原创 使用Redis实现延时队列

延时队列相比于普通队列最大的区别就体现在其延时的属性上,普通队列的元素是先进先出,按入队顺序进行处理,而延时队列中的元素在入队时会指定一个延迟时间,表示其希望能够在经过该指定时间后处理。从某种意义上来讲,延迟队列的结构并不像一个队列,而更像是一种以时间为权重的有序堆结构。可以看到生产者很简单,其实就是利用zset的特性,给一个zset添加元素而已,而时间就是它的score。消费者的代码也不难,就是把已经过期的zset中的元素给删除掉,然后处理数据。redis的zset实现延迟队列。

2024-04-25 11:37:59 77

原创 未加@transational注解的A方法调用加了@transational的B方法 ,事务会生效吗

然而,如果这个有注解的方法是被同一个类中的其他方法调用的,那么该方法的调用并没有通过代理类,而是直接通过原来的那个bean,所以就不会启动transaction,我们看到的现象就是@Transactional注解无效。我们调用的方法A不带注解,因此代理类不开事务,而是直接调用目标对象的方法。当进入目标对象的方法后,执行的上下文已经变成目标对象本身了,因为目标对象的代码是我们自己写的,和事务没有半毛钱关系,此时你再调用带注解的方法,照样没有事务,只是一个普通的方法调用而已。

2024-04-25 11:19:39 83

原创 inner join和left join哪个效率更高

①大家都知道,sql尽量使用数据量小的表做主表,这样效率高,如果使用数据量大的表做主表,此时使用left join 就会比较慢,即使关联条件有索引。②选择inner join还有个好处,不会产生null,有些表我们在定义的时候某些字段不允许存在null,如果用left join就可能会产生null,此时软件就会报错,而inner join可以避免。③在实际运用中选择inner join还是left join这个需要根据实际场景进行选择,并不是所有的地方都能用inner join的,建议能用则用。

2024-04-25 11:01:59 72

原创 一条sql发送给mysql后,内部是如何执行的?(说一下 MySQL 执行一条查询语句的内部执行过程?)

1、mysql在接受到一条查询时,如果开启了查询缓存,会先从查询缓存里取,没有的话进入下一步2、进入解析阶段,解析器会通过关键字将sql解析成一颗解析树,这里会进行词法和语法的解析。之后预处理器会将解析树进一步分析,检查数据表和列是否存在,最后预解析器会生产一颗新的解析树,并将解析结果传给执行优化器。3、执行优化器会将解析树转换成一个执行计划,这里会对语句做一些优化,比如子查询转换成连接查询。这个执行计划里会声明用哪些索引,,可以使用explain查看。

2024-04-19 23:15:22 377 1

原创 synchronized锁升级原理

轻量级锁就是线程在占有锁的时候,将锁对象的对象头复制一份到自己的栈帧中,然后使用CAS将锁对象头里的内容换成栈帧的地址。当一个线程获取锁时,会从锁对象的对象头立获取线程id和自己比较,如果是一致,就直接加锁,偏向锁它是适用于一个线程多次获得同一个锁的情况。synchronized锁有四种状态,无锁,偏向锁,轻量级锁,重量级锁,这几个状态会随着竞争状态逐渐升级,锁可以升级但不能降级,但是偏向锁状态可以被重置为无锁状态。升级成重量级锁之后,重量级锁会把除了拥有锁的线程都阻塞掉,防止CPU空转。

2024-04-19 23:04:40 233

原创 四种引用-面试

虚引用:对象回收跟踪(一个对象是否有虚引用存在,不会决定对象的生命周期,就相当于没有引用。软引用:内存不足立即回收。

2024-04-19 22:32:18 73

原创 Java类加载

实现:接口定义在启动类加载器中,实现类定义在其他类加载器,当启动类加载器需要加载其他子类加载器路径中的类,class文件加载到内存,再到类卸载出内存会经历7个阶段:加载、验证、准备、解析、初始化、使用、和卸载。类加载器接到加载类的请求,就委托给父类进行加载,父类加载不了才自己加载。可见性:子类可以访问父类加载的类,父类不能访问子类的。3、线程上下文类加载器,能够让父类调用子类进行加载。双亲委派模型:找父类加载,父类加载不了再自己加载。缺点:父类无法加载子类的类。优点:可以避免重复加载。

2024-04-15 16:04:56 238

原创 mysql面试

是innodb的一个特殊功能,当某些索引值被使用地非常频繁,会在内存中,基于B-tree之上再创建一个哈希索引,这是一个完全自动的内部行为,用户无法控制。

2024-04-13 20:44:26 731

原创 多线程面试准备

CAS的优势在于它没有阻塞状态,不会引起线程上下文的切换和调度问题。如果大于等于,判断等待队列是否满,如果满了,线程数是否小于最大线程数,是->创建新线程执行任务,不是则拒绝。WorkStealingPool:工作窃取线程池,Java8引入的一种线程池,每个线程维护自己的任务,可以窃取别的线程队列中的任务。FixedThreadPool:固定大小的线程池,核心线程数和最大线程数相同,适用于任务量可控、并发量不是很大的场景。6、线程工厂:新建线程,可以设置线程的优先级、线程名、线程类型用户线程/守护线程等。

2024-04-13 20:31:53 250

原创 rocketmq面试

4、Producer发送消息,启动时先跟NameServer集群中的其中一台建立长连接,并从NameServer中获取当前发送的Topic存在哪些Broker上,轮询从队列列表中选择一个队列,然后与队列所在的Broker建立长连接从而向Broker发消息。具体流程是,消息写入内存的PAGECACHE后,立刻通知刷盘线程刷盘, 然后等待刷盘完成,刷盘线程执行完成后唤醒等待的线程,返回消息写成功的状态。异步刷盘:在返回写成功状态时,消息可能只是被写入了内存的PAGECACHE,写操作的返回快,吞吐量大;

2024-04-13 20:29:11 654

原创 Redis面试

先更新mysql,如果删除redis失败,将删除操作发送到mq,过一会再删除,重试删除操作。可预知的:凭借业务经验,进行预估哪些是热key,通过批量加载和预先访问热门数据,将热key提前加载到内存中。启动时,哨兵会选举出一个主节点,每个哨兵节点向其他节点发出命令,当票数大于一半时就成为领导者。节点监控,发送命令周期性的检查主从节点的状态,如果发现主节点不可用,触发一次故障转移。monitor 哨兵进程,监控主节点和从节点的情况,并通知其他哨兵进程。如果数据库也没有的数据,在缓存做一个空的值,防止缓存穿透。

2024-04-13 19:45:12 494

原创 Dubbo面试回答简单版

调用之前生成的代理类,从cluster中经过负载均衡等选择一个invoker进行调用,会记录请求和请求id,服务端根据参数选择exporter,调用真正的实现类,得到结果后,根据请求id将结果放到等待的线程中,消费者最后得到响应。每次发起调用时,都会按照本地的地址列表,以负载均衡的策略去进行调用。注册中心之间保持TCP长连接,后续每个节点有任何数据变化的时候,注册中心会根据watcher的回调主动通知客户端(事件通知),客户端接到通知后,会把对应节点下的全量数据都拉取过。它可以把我们对接口的配置,

2024-04-13 17:17:11 943

原创 Spring AOP IOC

BeanFactory是Spring里面最底层的接口,是IoC的核心,定义了IoC的基本功能,包含了各种Bean的定义、加载、实例化,依赖注入和生命周期管理。**概念:**依赖控制反转,在IOC之前,一个对象要引入另一个对象就要自己new,用完之后也要自己释放,对象之间耦合较深,出现IOC之后,由spring来控制对象注入,引用对象只需要用就可以了,不需要再管理注入对象的生命周期。在内存中生成一个aop对象,包含原对象的所有方法,并在切点执行完成后调用原对象的方法。**DI:**依赖注入。

2024-04-13 17:11:06 849 1

原创 Map相关面试答案(都是简单版

1、继承2、红黑树实现,返回有序的key3、在创建时需要提供comparator来排序。

2024-04-12 23:18:08 426

原创 慢查询的处理

经常用在where、order by、分组、连接的、更改少的、1、先用explain看下。2.2 如何选择索引。

2024-04-12 20:26:48 126

原创 OOM的处理流程

jmap: JVM memory map 生产jvm的内存转储快照、生产heapdump文件 查询finalize执行队列。jstat:JVM statistics monnitoring 查看jvm各方面的运行数据 可以看堆的容量和已使用空间。使用jps和 jstat -gcutil 156 1000 10 命令查看 刚重启后与即将OOM的机器GC情况。dump OOM前堆快照,查看当前存在哪些大对象(实例数量最多,占用内存空间比例最大的),找到大对象引用。第一种会突然变多,第二种是缓慢增加的,

2024-04-12 20:15:06 182

原创 ZGC的介绍

ZGC中取消了分代的设计,并将内存空间按页面的形式来分,ZGC的垃圾回收线程和业务线程同时运行,ZGC是一个高度并发的垃圾回收器,多个线程进行回收,只有短暂的STW同步暂停。在ZGC中使用了标记-复制算法。ZGC 周期由三个 STW 暂停和四个并发阶段组成:标记/重新映射( M/R )、并发引用处理( RP )、并发转移准备( EC ) 和并发转移( RE )ZGC只有三个阶段是STW的,其他阶段完全并发。

2024-04-12 19:06:09 331

原创 策略模式、模板模式、观察者模式

其用意是针对一组算法,将每一个算法封装到具有共同接口的独立的类中,从而使得它们可以相互替换。观察者模式是一种行为型设计模式,它定义了一种一对多的依赖关系,当一个对象的状态发生改变时,其所有依赖者都会收到通知并自动更新。写一个接口,然后写多个类继承这个接口,每个类实现不同的逻辑,用一个context来放会用到的参数,。提供一个模板,将公共逻辑写到模板类里,将其中需要不同实现的方法拆出来定义,让子类去实现。其主要目的是通过定义相似的算法,替换if else 语句写法,并且可以随时相互替换。

2024-04-12 17:05:58 380

原创 接口优化思想

一是我使用了预取、异步、批量、远程调用并行、空间换时间、池化、在正式执行判断逻辑前,先将每个订单的订单信息、用户信息、历史信息、以及远程调用其他系统的信息全部通过线程池多线程异步调用,预先准备好,缓存在map里。我需要做一个展示页面,这个页面涉及的订单号特别多,每个订单号都要查询订单信息,并且需要展示多条内容,每条内容都要拼接并判断逻辑。但是将查询的从主库改成从库,这只是一个查询的接口没必要用主库。查其他系统每次接口的耗时是p99,每个订单都要调用一次。2、异步:耗时操作放到异步执行。

2024-04-12 15:33:10 198

原创 spring的事件推送

观察者模式是一种行为型设计模式,它定义了一种一对多的依赖关系,当一个对象的状态发生改变时,其所有依赖者都会收到通知并自动更新。在 Spring 的事件机制中,我们可以令一个事件类继承 ApplicationEvent 类,然后将实现了 ApplicationListener 的 Bean 注册到 spring 容器,最后向 ApplicationEventPublisher 推送事件对象即可令所有订阅者收到事件。

2024-04-12 15:20:48 314 1

原创 dubbo2和dubbo3区别

dubbo3:beanName根据当前添加的beanDefinition class,再加上“#编号”,如 org.apache.dubbo.config.spring.ServiceBean#0、org.apache.dubbo.config.spring.ServiceBean#1。“reference bean id不同,接口相同,registry不同” 场景下, 只订阅了一个registry的服务,原因是。找到的prevConfig相同(地址相同,或除了id意外的其它属性值均相同),则返回。

2024-04-12 14:14:37 903

原创 jdk8升级到jdk17

jdk8新特性:1、lambda表达式2、引入了stream api3、函数式接口4、方法引用 ::5、hashmap实现的增强6、Optional类7、对时间、日期的优化,新增了LocalDate、LocalTime、LocalDateTime,打印输入时比date友好。5、并发增强:JDK 8对并发编程进行了增强。它引入了一些新的并发工具和类,使得并发编程更加容易和有效。其中包括CompletableFuture类、StampedLock类、并行数组等。

2024-04-11 20:29:04 697

原创 单例模式的双重检查锁

过了第一层检查后就进入synchronized,同步代码块,在同步代码块中再次检查,防止有多个线程同时进入同步代码块。实例变量需要用volatile修饰,这样多个线程才能看见。第一层检查是判断实例是否已经被创建。

2024-04-11 17:54:58 592

原创 jvm的面试回答

1、jvm由本地方法栈、虚拟机栈、方法区、程序计数器、堆组成,其中堆和方法区是线程间共享的,程序计数器、虚拟机栈和本地方法栈是线程私有的。2、虚拟机栈:保存每个java方法的调用、保存局部变量表、等栈可能出现内存溢出,如果出现调用方法死循环,会出现栈溢出,stackoverflow。3、oom和stackOverflowOOM是内存溢出,内存不足线程太多导致的。stackoverflow是栈溢出,调用的方法太深了会这样,可能是调用出现了死循环。4、本地方法栈。

2024-04-11 17:23:33 1429

原创 mvcc面试答法

MVCC就是多版本并发控制,一行数据有多个版本的数据。每个事务在第一次读取时都生产一个快照读的视图,只能读这个视图记录的之前的数据版本。而事务提交时,则会记录在undo log里,数据会有隐藏字段用来记录最新修改本记录的事务id,并指向上次修改的数据。视图里具体是记录当时活跃的事务id,用来判断哪个版本的数据可用。用于查询的时候从新到旧搜索。最终找到早于事务开始提交的数据。

2024-04-10 23:19:29 64

原创 处理慢查询时使用explain一般看哪些字段

Using filesort:当 Extra 中有 Using filesort 时, 表示 MySQL 需额外的排序操作, 不能通过索引顺序达到排序效果. 一般有 Using filesort, 此时建议优化sql,一般会将排序的逻辑放在代码里实现。select_type就是查询类型,在我司的业务里基本上用的都是简单查询,在内存中处理逻辑,复杂查询的话排查问题比较麻烦,引起慢查询还会拖累数据库,数据库里还有别的应用的。如果出现index和extra:using index ,代表使用的是覆盖索引。

2024-04-10 22:46:58 176

原创 线程间共享内存的方式

我处理过一个多个线程处理数据的,需要做一个暂停功能,用的就是在redis设置一个暂停信号量,每个线程在循环里都会检查这个信号,如果为true就结束工作。因为一个应用基本上都会有多台机器,多台机器间的线程通信,最好用redis来做。2、在企业级应用里,应当使用外部存储,比如redis。1、volatile,共享内存,在同一机器上的。

2024-04-10 22:28:56 108

原创 mq消息不丢失不重复

不重复的话,用的redis,记录已发送到接收方的消息id,如果在redis里有就不再重复发。不丢失的话,用的是存入mysql的方式,先存在缓存中,再一次刷盘,记到磁盘里。如果在消费过程中出现异常,需要人工处理,并支持手动重发。

2024-04-10 22:23:36 99

原创 索引失效的场景(简单版)

2、索引参与了运算、使用了函数、出现了隐式转换、使用like时前面加了%、使用了is not null 、not exist。1、没有符合最左匹配原则,索引的顺序不符合最左匹配原则。

2024-04-10 22:09:59 64

原创 如何保证Redis和数据库数据一致性

第二次删除去掉第一次删除缓存和更新过程中产生的脏数据。

2024-04-10 20:44:47 62

原创 @Transactional(readOnly=true)不能提升查询效率,只能用于保证事务隔离级别

开启这个会增加aop的损耗,相比不加这个,可以帮助保证事务隔离级别为可重复读。

2024-04-10 20:09:27 261

原创 dubbo:Channel

在send方法中,先调用父类的send方法检查channel是否关闭,然后调用netty channel 进行发送消息,如果是需要sent反馈的话,就获取配置的timeout 超时时间,缺省是1s,等待timeout超时时间获取发送状态,如果发送状态是false,或者出现了异常,则会抛出异常。继承了Endpoint,Endpoint表示端点的意思,客户端,服务端都可以认为是一个端点,Endpoint主要抽象了端点的关闭,发送消息,获取本端点的地址等。ChannelHandler handler来维护。

2024-01-22 19:17:41 370

原创 dubbo:传输TRANSPORTER

这是与远程通信的过程相关的,网络传输的数据必须是二进制数据,但通常调用方请求的入参有可能是对象(各种面向对象语言),而对象是不能直接在网络中传输的,所以需要把它转成可传输的二进制串,并且要求转换算法是可逆的,这个过程也就是“序列化”过程。第三层:proxy 层,服务代理层,透明生成客户端的 stub 和服务单的 skeleton,调用的是接口,实现类没有,所以得生成代理,代理之间再进行网络通讯、负责均衡等;第二层:config 层,配置层,主要是对 Dubbo 进行各种配置的,Dubbo 相关配置;

2024-01-22 19:15:27 368

原创 dubbo:异步

Provider端异步执行将阻塞的业务从Dubbo内部线程池切换到业务自定义线程,避免Dubbo线程池的过度占用,有助于避免不同服务间的互相影响。异步执行无异于节省资源或提升RPC响应性能,因为如果业务执行需要阻塞,则始终还是要有线程来负责执行。Provider 端异步执行和 Consumer 端异步调用是相互独立的,可以任意正交组合两端配置。Consumer异步 - Provider同步。Consumer同步 - Provider异步。Consumer异步 - Provider异步。

2024-01-22 19:13:45 353

原创 dubbo:服务暴露

ServiceConfig描述了对外提供的服务,ref属性引用了具体的服务实现对象,当Provider接收到Consumer发起的RPC调用时,会交给ref执行,但是Dubbo不会直接使用ref,因为不管是Provider还是Consumer,Dubbo都在向Invoker靠拢。有了Invoker就可以通过Protocol根据协议进行服务暴露,如果服务需要注册,Dubbo会改写URL协议为registry,这是个伪协议,只是在原服务暴露的基础上,增加了服务注册的功能。它可以把我们对接口的配置,

2024-01-22 19:12:11 885

原创 dubbo:深入理解Apache Dubbo与实战

服务提供者启动时,会广播自己的地址。ZooKeeper注册中心采用的是“事件通知” + “客户端拉取”的方式,客户端在第一次连接上注册中心时,会获取对应目录下全量的数据。注册中心之间保持TCP长连接,后续每个节点有任何数据变化的时候,注册中心会根据watcher的回调主动通知客户端(事件通知),客户端接到通知后,会把对应节点下的全量数据都拉取过。ZooKeeper是官方推荐的注册中心,在生产环境中有过实际使用,具体的实现在Dubbo 源码的dubbo-registry-zookeeper模块中。

2024-01-22 19:10:18 1169

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除