java
文章平均质量分 64
跟心爱的人浪迹天涯
Java小学生
展开
-
Spring框架下使用策略模式
策略模式, 即根据不同的参数, 调用不同业务流程, 但各流程的逻辑基本类似.真实场景:支付路由, 根据不同的渠道参数, 进行不同的调用. 但具有类似逻辑: 参数校验->本地创建订单->发送请求->根据结果做不同的处理.AbstractChannel抽象类, 定义了各渠道的整体架构public abstract class AbstractChannel { public void handle() { check(); createOrd原创 2021-04-29 12:31:17 · 290 阅读 · 1 评论 -
Java使用easyexcel实现导入导出功能
Easyexcel是阿里开源的, 简单, 可快速集成的excel文件导入导出工具, 能够有效的节省内存, 避免出现OOM问题. 原理: 不是一次性将内容全部读取, 而是一行行读取, 从而降低内存的使用.pom.xml<dependency> <groupId>com.alibaba</groupId> <artifactId>easyexcel</artifactId> <version>2.1.7</versio原创 2021-04-28 10:25:40 · 1434 阅读 · 0 评论 -
RocketMQ消息生产过程 源码解析
示例首先写一个生产消息的实例, 代码入口@Autowiredprivate RocketMQTemplate rocketMQTemplate;public String sendMsg(String topic, String msg) { Message<String> message = MessageBuilder.withPayload(msg).build(); SendResult result = rocketMQTemplate.syncSend(to原创 2021-02-28 13:17:47 · 667 阅读 · 0 评论 -
Spring Async注解 方法异步调用 用法 源码解析 以及错误使用解决方法
Async是Spring新加入的一种异步机制, 大多开发者也只是停留在会用的水平, 对其原理不太了解, 作为一名开发人员, 我们不仅要知其然, 更要知其所以然, 才能在项目开发过程中不会踩到不必要的坑.用法1.在SpringBoot启动类添加注解@EnableAsync@EnableAsync@SpringBootApplicationpublic class WebApplication { public static void main(String[] args) {原创 2021-01-17 01:27:08 · 1118 阅读 · 0 评论 -
解决java@RequestBody中枚举不匹配问题 空字符串转枚举异常
异常org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Cannot deserialize value of type *.**.**.TaskStatusEnum from String “”: value not one of declared Enum instance names: [0, 1, 2]; nested exception is com.fasterxml.jac原创 2021-01-15 13:16:08 · 6253 阅读 · 4 评论 -
JVM GC 收集器 类加载 性能调优笔记
对象可回收引用计数法 循环引用可达性分析法 GC Roots对象栈中对象方法区中常量/静态属性对象本地方法栈中对象可回收区域新生代 老年代 永久区(废弃的常量/类)回收算法 标记不被回收的对象标记清除算法 碎片复制算法 浪费一半空间标记整理算法分代回收算法 新生代(分代/标记清理) 老年代(标记整理)收集器Serial 单线程 复制算法 stw 没有线程切换 效率高ParNew Serial多线程版本 可通过-XX:ParallelGCThreads限制线程个数Paral原创 2020-12-02 20:33:01 · 196 阅读 · 0 评论 -
SpringBoot添加Swagger2支持 可直接供前端及测试使用 生产环境禁用
pom.xml<dependency> <groupId>io.springfox</groupId> <artifactId>springfox-swagger2</artifactId> <version>2.7.0</version></dependency><dependency> <groupId>io.springfox</grou原创 2020-12-02 16:49:49 · 380 阅读 · 0 评论 -
idea和jvisualvm工具模拟sql查询导致OOM问题排查过程 经典面试
idea配置配置application启动参数, 记录发生OOM时dump一下堆信息-Xms100m -Xmx100m -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/tmp/heapdump.hprof -Dfile.encoding=utf-8数据库添加数据delimiter $$SET AUTOCOMMIT = 0$$create procedure insert_data()begindeclare insert_count d原创 2020-12-01 17:34:35 · 508 阅读 · 0 评论 -
Spring解决循环依赖-源码分析
首先从doGetBean开始分析, 此时容器已初始化完成, 开始执行bean的初始化protected <T> T doGetBean( final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly) throws BeansException ...原创 2020-11-27 17:32:44 · 120 阅读 · 0 评论 -
Java自己实现一个LRU算法
LRU(Least Recently Used) 最近最少使用算法 在指定空间内, 存入元素时, 判断是否存在, 将其放置队列一端(如有取代旧元素). 当队满, 再添加新的元素时, 删除队列另一端的元素.由于元素会频繁移动, 所以不能使用Array, 应考虑使用链表实现.方案一LinkedHashMap 是一个保存了元素插入顺序的HashMap.accessOrder属性, 插入或获取元素时, 都会将其放入队尾.removeEldestEntry方法, 是否删除最老的元素, 每次插入元素时都会被执原创 2020-11-27 12:48:28 · 332 阅读 · 0 评论 -
JUC 多线程并发同步工具类原理及源码解析 聚合
**JUC(java.util.concurrent)**包下的类都是用于高并发, 多线程的, 包含了ConcurrentHashMap, 原子操作类, ReentrantLock, AQS等. 也是面试过程中最常问的java基础题. 搞清楚各工具类的原理有助于我们编程水平的提升, 也在面试的过程中增加自信心.ConcurrentHashMapHashMap的线程安全方式, 与1.7有不同, 使用cas和synchronize关键字实现线程安全ConcurrentHashMap原理解析Atomic原原创 2020-11-20 18:56:01 · 260 阅读 · 0 评论 -
ConcurrentHashMap原理解析
ConcurrentHashMap是HashMap在多线程下使用方式,采用分段锁原理。在JDK7和JDK8中实现原理不同, JDK7中使用标准分段锁,默认为16段,可设置,一旦设置不可修改,锁粒度大,通过ReentrantLock实现锁。JDK8中通过使用CAS和synchronize关键字实现,本文我们通过源码来解析ConcurrentHashMap的原理。数据结构ConcurrentHashMapd的组成是有数组+链表+红黑树实现的,JDK8中HashMap和ConcurrentHashMap结构类原创 2020-11-20 17:54:10 · 420 阅读 · 0 评论 -
ReentrantReadWriteLock可重入读写锁源码解析
ReentrantReadWriteLock 可重入读写锁,内部维持了ReadLock和WriteLock,分为公平锁和非公平锁,由于读锁和写锁使用了同一个Sync对象,所以如果第一次获取锁失败,都会被放入同一个队列中。底层使用了AQS,state高16位表示共享锁-读锁,低16位表示独占锁-写锁。1. 如果一个线程持有了读锁,不能再持有写锁2. 说明如果一个线程持有了写锁 可以再持有读锁3. 锁可以降级(写锁->读锁) 不能升级(读锁->写锁)源码public class Reent原创 2020-11-17 16:12:22 · 108 阅读 · 0 评论 -
Semaphore信号量使用及源码分析
Semaphore 信号量控制,用于动态指定同时执行线程个数。比如行车,指定总共10车道,有的车占2个车道,有的占1个,当车道被释放后其他车辆才能进入。Semaphore 底层是用AQS共享锁实现,通过改变state和线程占用信号量大小判断是否获取锁,有公平和非公平两个机制。公平锁效率低,不会出现线程饥饿现象,非公平锁并发量高,可能会出现线程饥饿现象。示例public static void main(String[] args) { int[] threadCount = new int[]原创 2020-11-17 12:35:48 · 130 阅读 · 0 评论 -
ReentrantLock可重入锁、公平锁、非公平锁源码分析
ReentrantLock 可重入锁,实现了公平锁和非公平锁两种机制,主要区别就是非公平锁会先获取锁,如果成功,会插队执行,而非公平锁会直接进入队列,依次执行。非公平锁并发量大,性能高,但是有可能出现线程饥饿现象。ReentrantLock 底层使用AQS独占锁为基础实现同步机制,重写了tryAcquire和tryRelease方法,分别用来获取锁和释放锁。可重入是通过exclusiveOwnerThread和state值来控制的,获取锁时判断是否是持有锁线程,如果是,获取成功,否则入队列。源码pub原创 2020-11-17 11:04:02 · 154 阅读 · 0 评论 -
CyclicBarrier和CountDownLatch源码解析
CyclicBarrier 循环内存屏障,对象可重复使用,用作多个线程同时满足一个条件,然后一起运行,比如打车,司机和乘客都到达之后,才能启动订单。底层使用了可重入锁,维护一个count,每次执行await方法,count减1,至0后,执行主线程,唤醒阻塞线程,并重置CyclicBarrier 对象。属性// 重入锁private final ReentrantLock lock = new ReentrantLock();// 释放锁条件private final Condition trip原创 2020-11-16 16:57:28 · 131 阅读 · 0 评论 -
线程池ThreadPoolExecutor原理及使用分析
日常开发中, 如果我们需要使用线程执行某些业务, 在阿里开发手册中有明确约定:线程资源必须通过线程池提供,不允许在应用中自行显式创建线程。下面我们来分析以下线程池ThreadPoolExecutor的原理及优点线程池的优点可以控制线程并发数量减少线程的创建和销毁过程,提升效率可以对线程进行管理构造方法及参数说明public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize,原创 2020-11-12 18:15:32 · 197 阅读 · 0 评论 -
SpringCloud使用Nacos做注册中心和配置中心
Nacos是阿里生态下, 用于微服务注册与发现、配置管理实时刷新的微服务平台. 默认使用嵌入式持久化, 可支持MySQL数据库持久化安装Nacos服务1.下载nacos服务 版本 1.3.2 Windows下下载zip包并解压2.可使用默认方式持久化, 跳过此步骤. 如果使用mysql, 需要创建数据库nacos, 执行conf/nacos-mysql.sql, 并修改application.properties, 配置MySQL连接信息### If use MySQL as datasource:原创 2020-10-25 09:59:28 · 1286 阅读 · 1 评论 -
BlockingQueue阻塞队列的实现方式及源码解析
BlockingQueue阻塞队列, 分为有界和无界队列, 常用的有界队列即为ArrayBlockingQueue, 无界队列即为LinkedBlockingQueue, 虽然也有最大长达, 但最大长度为Integer.MAX_VALUE(21亿+).BlockingQueue接口中有以下方法public interface BlockingQueue<E> extends Queue<E> { // 添加元素, 如果已满, 抛出异常 boolean add(E e);原创 2020-08-16 11:30:52 · 419 阅读 · 0 评论 -
并发锁底层支持AQS(AbstractQueuedSynchronizer)原理及源码解析
AQS是AbstractQueuedSynchronizer的简写, 是由Doug Lea大神所写, 为并发类ReentrantLock ContDownLatch CyclicBarrier等提供了基础的支持, 是一个抽象类, 封装了一些通用方法.AQS的原理就是在执行时先判断state是否满足执行条件, 如果满足, 则执行线程, 如果不满足, 则添加到等待链表中.主要有以下重要参数private transient volatile Node head;private transient vo原创 2020-08-15 23:15:29 · 133 阅读 · 0 评论 -
使用AtomicReference类通过自旋和CAS简单实现自定义可重入锁
AtomicReference是原子引用并发类,内部通过调用Unsafe的本地方法CAS实现。下面我们使用CAS和自旋实现一个简单的可重入锁。自旋省去了线程的切换,但是空循环增加了对CPU的消耗。首先,定义MyReentrantLock类,有lock加锁和unlock释放锁,加锁设置超时时间,AtomicReference内部保存当前获取到锁线程的ID。import java.util.concurrent.atomic.AtomicReference;public class MyReentra原创 2020-08-14 11:09:52 · 398 阅读 · 0 评论 -
ArrayList HashMap非线程安全 List和Set线程安全实现方式
众所周知ArrayList是非线程安全的,内部采用Object[]数组实现,提供add、remove等操作。以下我们通过源码分析以下,如何线程不安全。public class ArrayTest { public static void main(String[] args) { List list = new ArrayList(); for (int i = 0; i < 10; i++) { new Thread(() ->原创 2020-08-13 19:43:40 · 610 阅读 · 0 评论 -
Atomic并发原子类源码及使用示例 解决ABA问题
Atomic原子操作类是JUC包下的类,包含AtomicInteger、AtomicBoolean、AtomicLong等等,使用volatile和CAS(比较并交换)完成操作。volatile是java关键字,轻量级的同步机制,用来保证变量的可见性,用于多线程。线程的操作是在线程私有的工作内存中,而变量的存储是在主内存中,所以线程修改变量时先把变量copy到工作内存中,操作完成后回写到主内存。volatile保证了变量可见性,当一个线程修改变量后,会将结果写到主内存中,并通知其他线程变量已被修改,需要重原创 2020-08-13 11:53:48 · 524 阅读 · 0 评论 -
使用synchronize和RenentrantLock循环打印指定量数字或字母ABC
使用synchronize关键字,优点:1.不需要手动解锁,不会造成死锁2.JDK1.8之后对其进行升级优化,性能和ReentrantLock相当3.可重入锁缺点:1.不能终止锁2.非公平锁3.解锁后唤起任意阻塞线程public class LoopPrint { public static volatile Integer index = 0; public static final int THREAD_COUNT = 3; public static fina原创 2020-08-06 17:59:54 · 237 阅读 · 0 评论 -
CyclicBarrier和CountDownLatch用法
CyclicBarrier用于多个线程在等待一个条件, 满足后全部继续执行。测试场景,考生挨个入场,全部到场后,开始发放试卷做题public static void main(String[] args) { CyclicBarrier barrier = new CyclicBarrier(10, () -> System.out.println("开始考试...")); for (int i = 0; i < 10; i++) { new Thread(()原创 2020-08-06 16:32:14 · 184 阅读 · 0 评论 -
Spring AOP用法及原理
AOP作为Spring的第二大核心内容,日常开发中,也是经常会用到的。所谓面向切面编程,就是对某些特定的方法执行的前后切入一些特定的代码。核心原来采用动态代理实现。使用场景日志 在方法执行前后打印日志事务 在方法执行前开启事务,执行完提交事务,异常回滚事务权限校验 在方法执行前对用户的登录状态及权限做校验使用方法步骤如下1.添加Aspect依赖<dependency> <groupId>org.springframework</groupId>..原创 2020-07-10 14:02:25 · 148 阅读 · 0 评论 -
Spring各种注解及含义
@Configuration注解在类上,标记此类是一个配置类,Spring会扫描到配置类并读取内部配置@ComponentScan注解在类上,用于指定spring扫描组件的包路径,可以为数组;还可以进行筛选过滤:excludeFilters includeFilters可以按照类型、正则、自定义(实现接口)、注解、AspectJ@Controller @Service @Repository @Component都是用来标记Spring容器组件的,只是场景不同;Controller Service原创 2020-07-09 14:17:32 · 3356 阅读 · 0 评论 -
SpringMVC页面访问流程(源码解析)
SpringMVC有五大核心组件, DispatcherServlet, HandlerMapping, Controller, ModelAndView, ViewResolver; 其中以DispatcherServlet最为核心, 以下简称ds, 类似电脑cpu.当容器接收到请求后, 会先到xml中找到对应servlet, 本质就是ds, 然后ds父类的service方法进行处理, 最后进...原创 2019-11-23 00:01:57 · 281 阅读 · 0 评论 -
SpringMVC初始化源码解析(基于XML配置)
熟悉SpringMVC的同学都知道SpringMVC的核心是DispatcherServlet(以下简称ds), 由于继承了HttpServlet, 所以它本质就是servlet, 当我们使用tomcat或其他Web容器启动项目时, 会先扫描项目的web.xml文件, 我们会在该文件中指定ds的具体路径, 并设置启动load-on-startup即加载此ds, 然后容器会自动调用ds父类中的ini...原创 2019-11-22 23:24:55 · 183 阅读 · 0 评论 -
zookeeper配置集群(Windows)
zookeeper的选举及宕机都是以过半作为机制的, 所以, 通常节点的个数为奇数个, 我们搭建3个zk节点, 使用同一个安装包下载zookeeper, 自行从官网上下载配置zoo.cfgtickTime=6000initLimit=10syncLimit=5dataDir=/tmp/zookeeperclientPort=2181启动服务zkServer.cmd...原创 2019-11-19 11:20:52 · 188 阅读 · 0 评论 -
Spring AOP动态代理(JDK与CGLib)及类内部方法事务不生效原因解析
1.创建接口public interface UserService { // 模拟操作 boolean getById(String id);}2.创建实现类public class UserServiceImpl implements UserService { // 实现接口方法, 并返回结果 public boolean getById(String id) ...原创 2019-11-14 13:49:20 · 1339 阅读 · 1 评论 -
LeeCode 10: 正则表达式匹配
题目给定一个字符串 (s) 和一个字符模式 (p)。实现支持 '.' 和 '*' 的正则表达式匹配。'.' 匹配任意单个字符。'*' 匹配零个或多个前面的元素。匹配应该覆盖整个字符串 (s) ,而不是部分字符串。说明:s 可能为空,且只包含从 a-z 的小写字母。 p 可能为空,且只包含从 a-z 的小写字母,以及字符 . 和 *。示例 1:输入:s = "a...原创 2018-09-19 17:24:39 · 297 阅读 · 0 评论 -
LeeCode 18: 四数之和
题目给定一个包含 n 个整数的数组 nums 和一个目标值 target,判断 nums 中是否存在四个元素 a,b,c 和 d ,使得 a + b + c + d 的值与 target 相等?找出所有满足条件且不重复的四元组。注意:答案中不可以包含重复的四元组。示例:给定数组 nums = [1, 0, -1, 0, -2, 2],和 target = 0。满足要求的四...原创 2018-09-07 17:26:12 · 145 阅读 · 0 评论 -
LeeCode 42: 接雨水
题目给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。上面是由数组 [0,1,0,2,1,0,1,3,2,1,2,1] 表示的高度图,在这种情况下,可以接 6 个单位的雨水(蓝色部分表示雨水)。 感谢 Marcos 贡献此图。示例:输入: [0,1,0,2,1,0,1,3,2,1,2,1]输出: 6解题思路对于每一个节...原创 2018-09-07 15:34:23 · 235 阅读 · 0 评论 -
Java实现: 从一副扑克中随机抽取5张牌,判断是不是顺子(5张牌数字连续,大小王为任意数字)。
题目从一副扑克中随机抽取5张牌,判断是不是顺子(5张牌数字连续,大小王为任意数字)。代码import java.util.Arrays;import java.util.Random;/** * Created by GuanDS on 2018/8/23. */public class Check5Link { private static Random ra...原创 2018-08-23 20:05:27 · 4529 阅读 · 0 评论 -
Java实现: 12个高矮不同的人,排成两排,每排必须是从矮到高排列,且第二排比第一排对应的人高
题目12个高矮不同的人,排成两排,每排必须是从矮到高排列,且第二排比第一排对应的人高。求排列方式有多少种?代码import java.util.ArrayList;import java.util.List;/** * Created by GuanDS on 2018/8/23. */public class Row2 { private static Lis...原创 2018-08-23 18:40:27 · 1045 阅读 · 0 评论 -
Java实现: 解数独
题目编写一个程序,通过已填充的空格来解决数独问题。一个数独的解法需遵循如下规则:数字 1-9 在每一行只能出现一次。 数字 1-9 在每一列只能出现一次。 数字 1-9 在每一个以粗实线分隔的 3x3 宫内只能出现一次。空白格用 '.' 表示。 算法使用递归算法, 首先应获取第一个要填充的的位置, 即行和列, 优先处理候选值比较少的, 提升效率, 因为如果复杂度呈指数...原创 2018-08-30 18:47:04 · 2112 阅读 · 0 评论 -
3L, 5L, 8L三个水桶等分8L水 Java(递归, 穷举)
题目有三个容积分别是8升、5升和3升的水桶,其中容积为8升的水桶中有8升水,其它两个水桶是空的。三个水桶都没有刻度,问如何在不借助其它工具的情况下只使用这三个桶把8升水等分。代码import java.util.ArrayList;import java.util.LinkedHashSet;import java.util.List;import java.util.Set;...原创 2018-08-23 14:15:54 · 3202 阅读 · 1 评论 -
Java常见设计模式
设计模式是软件开发人员在软件开发过程中面临的一般问题的解决方案。这些解决方案是众多软件开发人员经过相当长的一段时间的试验和错误总结出来的。设计模式:创建型模式这些设计模式提供了一种在创建对象的同时隐藏创建逻辑的方式,而不是使用 new 运算符直接实例化对象。这使得程序在判断针对某个给定实例需要创建哪些对象时更加灵活。工厂模式(Factory Pattern); 抽象工厂模式(Abst...原创 2018-08-16 17:17:08 · 196 阅读 · 0 评论 -
SpringMVC整合WebSocket实现即时通讯
1. pom中添加socket支持: <dependency> <groupId>org.springframework</groupId> <artifactId>spring-websocket</artifactId> <version...原创 2018-07-27 17:38:35 · 6914 阅读 · 1 评论