- 博客(35)
- 收藏
- 关注
原创 AbstractQueuedSynchronizer源码研读笔记
AbstractQueuedSynchronizerAbstractQueuedSynchronizer简称AQS,常见的锁ReetrantLock就是AQS的实现,AQS的本质是一个双向链表。通过head和tail都可以操作整个队列。 +------+ prev +-----+ +-----+head| | <---- | | <---- | | tail +------+ +-----+ +-----+
2021-01-26 17:15:01 108
原创 类加载过程
加载主要作用:把编译好的class文件加载到内存中这个阶段主要是编译器把Java代码编译为class文件后,在启动jvm进程时,jvm会把class文件转为二进制数据存在内存中,然后在方法区创建一个对应Class对象,该对象是访问被加载过后的class对象各种数据的入口。验证主要作用:验证class(存在内存中的二进制码)是否符合当前jvm版本的规范,已经代码是否符合jvm的规范。当class文件被加载到内存后,先检验是否符合当前jvm版本规范,因为不同版本的jvm规范是不一致的,新的jv
2021-01-26 17:14:48 101
原创 String、StringBuilder、StringBuffer区别
可变性String通过查看String的源码可以发现,底层存储String内容的是一个char[]。该char使用了final修饰:String.class/** The value is used for character storage. */private final char value[];所以String是不可变的。StringBuilder、StringBuffer通过查看StringBuilder和StringBuffer的源码可以看到,它们都继承了抽象类Abstract
2021-01-26 17:14:34 160 3
原创 ReentrantLock中的CAS与volatile的state
先说结果,CAS与volatile都拥有内存可见性和内存屏障,也就是说cas具备与volatile一样的volatile读与volatile写。volatileReenteantLock 使用volatile来修饰了state变量,volatile具有这些特点:保证内存可见性,以及防止指令重排序。如何保证内存可见性底层通过使用lock指令来实现volatile。其中lock指令在多核处理器下会有以下操作:将当前处理器中缓存行中的数据立即写回主存。数据写回主存后,会导致其他线程所持有的旧数据的内
2021-01-25 11:18:08 537
原创 volatile关键字
volatile关键字作用实现共享变量的可见性。防止指令重排序。volatile修饰的变量是如何保证可见性的可见性问题:比如i++操作,在多线程环境下,i++中i的初始值为0,我们使用两个线程共同执行这个操作,理想结果是i的值为2,但是最后i的值可能为1,原因就是当线程1从主存中获取到0刷新到自己的高速缓存中。然后进行计算,在没有计算完毕时,或计算完毕还没来得及刷新到主存中时,线程2也去从主存中获取到0,然后刷新到自己的高速缓存中,然后进行计算。问题就在此时出现了。两个线程计算出来的结果变为
2021-01-25 11:17:51 73
原创 CopyOnWriteArrayList的add方法
源码分析是JUC包下提供的一个线程安全的ArrayList容器。使用了ReetrantLock来保证线程安全。add(E e) 往集合末尾添加一个元素 public boolean add(E e) { // 使用juc的可重入锁保证线程安全 // 其中lock在CopyOnWriteArrayList的定义:final transient ReentrantLock lock = new ReentrantLock(); final Reen
2021-01-25 11:17:36 702 1
原创 synchronized使用static修饰与不使用static修饰的区别
synchrinized该关键字是一个同步锁,就是当一个线程进入synchronized修饰的代码后,执行完毕之后,释放锁。其他线程才可竞争此锁。该锁可以用于锁代码块、锁实例方法、锁静态方法,但是其中是存在很大的区别的。question1使用synchronized修饰同一个类中的两个方法,使用同一个对象调用两个方法,最后的输出结果是什么?public class SynchronizedDemo { public static void main(String[] args) {
2021-01-25 11:17:23 493
原创 JUC里面常用到的各种锁
内存可见性问题多个线程操作同一个共享数据时,线程之间的操作是不可见的。解决方案1 synchronized优点重量级锁,具备互斥性、原子性、内存可见性(在持有锁期间,会完全把数据修改到主存后才会释放锁)。当一个线程已经访问共享数据时,该共享数据不可以被其他线程访问,需等当前线程释放锁以后,其他线程才可获取锁进行操作。缺点很明显,每个线程只能等待持有锁的线程释放锁,才可以操作被synchronized修饰的代码。这部分操作就是阻塞的,明显导致代码执行效率的降低。解决方案2 volati
2021-01-25 11:17:03 172
原创 JVM内存区域面试重点
程序计数器重点: 主要是与字节码指令的执行相关用于字节码解释器来指示线程下一步该做什么,比如:线程恢复、return、循环、异常处理等指令。为什么程序计数器是线程私有的?在多线程环境下,线程之间会互相切换运行。并不是真正的“并行”。所以当线程切换回来恢复后,需要知道该线程上次已经执行到什么地方了,并且需要独立存储,线程之间不应该互相影响。所以在程序计数器中,每个线程都应该有一个程序计数器,这样才能保证线程正确执行指令。程序计数器的生命周期程序计数器因为是线程私有的,所以当线程创建的时
2021-01-25 11:16:47 69
原创 Java集合框架源码研读后笔记
CollectionCollection是Java的一个集合容器抽象。这里面分为三种类型的集合容器:List、Set、Queue,其中List主要是提供类似数组一样的数据结构。Set提供不重复数据的数据结构。Queue提供队列来存储数据的方式。ListArrayList: 基于动态数组实现,保证添加数据的顺序。可以随机访问。Vector:实现与ArrayList差不多,但是是线程安全的。每个方法都直接使用synchronized修饰。现在基本不用。LinkedList:双向链表结构
2021-01-25 11:16:34 81
原创 centos 7+ 暴露端口给外网
暴露端口firewall-cmd --zone=public --add-port=/tcp --permanent重新加载防火墙firewall-cmd --reload查询是否暴露firewall-cmd --zone=public --query-port=/tcp查看本机开放的端口firewall-cmd --list-ports
2021-01-23 20:02:26 424
原创 Spark学习笔记总结
Spark与MapReduceSpark 运算比 Hadoop 的 MapReduce 框架快的原因是因为 Hadoop 在一次 MapReduce 运算之后,会将数据的运算结果从内存写入到磁盘中,第二次 Mapredue 运算时在从磁盘中读取数据,所以其瓶颈在2次运算间的多余 IO 消耗. Spark 则是将数据一直缓存在内存中,直到计算得到最后的结果,再将结果写入到磁盘,所以多次运算的情况下, Spark 是比较快的. 其优化了迭代式工作负载。Spark的Master节点与Worker节点Ma
2021-01-23 20:01:57 148
原创 Spring Cloud各核心组件的功能及作用
Spring Cloud Eureka服务发现与注册Eureka Clienteurela client存在于每个provider和consumer中。eureka client有以下动作:将本服务的信息注册到eureka注册中心。拉取注册注册中心的注册表,把各服务的注册信息缓存在本地中。定时向注册中心发送心跳(默认30s)保持通信并更新注册中心的注册表到本地注册表缓存中。如果超过90s没有发送心跳,则注册中心将会从注册表中将该服务删除。服务触发下线操作后,会主动请求注册中心删除该服务的信
2021-01-23 20:01:44 578
原创 几种限流策略
对于请求的限流主要有三种方式:计数器、漏桶算法、令牌桶算法。计数器记录每个请求的次数,限制请求每秒最多请求多少次,否则失效。这个方式比较简单粗暴。最明显的弊端就是,我限制了1秒内最多请求100次,但是在前10ms内已经请求完了100次,那么之后990ms相当于是空闲的,请求也无法再过来了。漏桶算法请求放在桶里面,排队放行。不管流量多大,多余的请求始终要在桶内排队,当桶内请求装满以后,之后的请求再也无法进来了。而且当瞬时请求很多的时候,漏桶算法也无法应对。实现方面:使用一个队列存储前台过来的请求,.
2021-01-22 17:07:20 400
原创 HashMap源码研读笔记
基本原理HashMap是一种key-value形式的键值对数据结构,每个键值对都是Entry,而Entry是一个链表,当hash过的key是相同的话,会放在Entry的next中。其实这也是因为hash碰撞的原因,使用hash虽然可以将数据均衡散列,但是也会避免不了通过hash算法得到的值是相同的情况。所以需要使用到链表结构,将hash相同但是key不相同的值放在同一个Entry链表中,也就是bucket中。其中HashMap默认容量是2 << 4也就是16,负载因子为0.75。阈值 = Ha
2021-01-22 17:06:24 93
原创 Spring Boot 2.0+ 与 JDK8全局替换LocalDateTime为时间戳
@Bean @Primary public ObjectMapper serializingObjectMapper() { ObjectMapper objectMapper = new ObjectMapper(); JavaTimeModule javaTimeModule = new JavaTimeModule(); javaTimeModule.addSerializer(LocalDateTime.class, new ...
2021-01-22 17:06:08 147
原创 HBase伪分布式搭建
之前把hbase安装配置好了–>HBase的安装、配置、使用,现在开始进行伪分布式的搭建。配置hbase-site.xml在原有的hbase-site.xml配置的基础上增加以下配置,该配置指示HBase以分布式模式运行,每个HBase相关的进程都是单独的JVM实例:<property> <name>hbase.cluster.distributed</name> <value>true</value></prope.
2021-01-22 17:05:50 505
原创 HBase的安装、配置、使用
下载进入hbase下载页面,选择与hadoop版本相兼容的hbase版本。在这个页面使用ctrl+f搜索"S", 然后下面有一个表就是hbase与hadoop版本对应关系:我这里使用的hadoop版本是2.8.5,使用的hbase版本是2.1.1。新建一个/usr/hbase目录,然后下载hbase。安装使用tar xzvf hbase-XXX命令解压hbase的包。解压完后,进入到解压好的hbase目录中,编辑conf/hbase-site.xml,该文件时主要的hbase配置文件,配置hb
2021-01-22 17:05:34 663
原创 Hadoop伪分布式搭建
下载及安装下载我先在CentOS 7.4的服务器的/usr/目录新建了一个hadoop目录,然后进入新建的hadoop目录,下载hadoop。命令: wget http://mirrors.hust.edu.cn/apache/hadoop/common/hadoop-2.8.5/hadoop-2.8.5.tar.gz到hadoop下载页面选择合适的hadoop版本进行下载,我使用的是2.8.5,截止现在,因为hbase最高支持2.8.X的版本,使用Hadoop2.9.X会有问题。安装把下
2021-01-21 10:05:56 74
原创 查找Linux系统中java安装位置
在购买云服务器以后,一般云服务器上面都会安装Java。但是在/etc/profile中一般没有配置JAVA_HOME,导致一些软件无法运行。使用以下步骤基本能找到Java的真实安装路径:先使用whereis java:whereis命令是定位可执行文件、源代码文件、帮助文件在文件系统中的位置输出如下:我们看到输出了一堆目录,然后使用ls -lrt /usr/bin/java:再使用ls -lrt /etc/alternatices/java:最后出现的/usr/lib/jvm/jav
2021-01-21 10:05:36 455
原创 hadoop相关命令
start启动NameNode: hadoop-daemon.sh start namenode启动DataNode:hadoop-daemon.sh start datanodeyarn启动resourcemanager:yarn-daemon.sh start resourcemanageryarn启动nodemanager:yarn-daemon.sh start nodemanageryarn启动historyserver:yarn-daemon.sh start historyserv
2021-01-21 10:04:18 75
原创 Hadoop完全分布式集群搭建遇到的一些问题
使用了3台在不同地区的服务器搭建集群,导致master机器的namenode无法启动的问题最开始遇到这个问题的时候,在master主机上使用jps命令发现master的namenode没有启动抵赖。于是我去看日志,发现报了一个BindException的错误。然后通过google先把/etc/hosts文件里面的ip映射改了一下,最开始是外网ip master这种方式配置的hosts。我改为了127.0.0.1 master,然后启动,发现namenode能正常启动了,但是去slave机器看的时候,
2021-01-21 10:03:49 583
原创 Spring boot 2.X启动报错:Specified key was too long; max key length is 1000 bytes
原因Spring boot 2.x默认使用的mysql 引擎为myisam,但是Spring boot2.0之前使用的是InnoDB,Spring boot2.0之后默认使用的是myisam引擎。然后在新建表的时候。就出这个错了解决在配置文件中加如下配置:spring: jpa: database-platform: # spring boot 2.0 的坑, spring boot2.+后默认使用的是MyISAM引擎 org.hibernate.dial
2021-01-21 10:03:12 130
原创 Spring Cloud踩坑记录
报错 Whitelabel Error Page原因是把Application.java放在了如下所示:解决: 把Application.java放到最外层即可解决启动报错ClassNotFoundException: feign.Feign$Builder原因: 包的问题。解决方案, 修改pom文件 <properties> <project.build.sourceEncoding>UTF-8</project.build.source
2021-01-21 10:02:51 129
原创 Docker安装并运行ElasticSearch-Head插件
使用docker安装es-head插件es-head插件支持es几个版本。Elasticsearch 5.x: docker run -p 9100:9100 mobz/elasticsearch-head:5Elasticsearch 2.x: docker run -p 9100:9100 mobz/elasticsearch-head:2Elasticsearch 1.x: docker run -p 9100:9100 mobz/elasticsearch-head:1我使用的是Ela
2021-01-21 10:02:41 451
原创 Docker将本地目录挂载到容器
背景因为在服务器上安装了elasticsearch,还需要装一个ik插件到elasticsearch中去,如果直接去docker容器里面去安装该插件,肯定还需要很多额外操作,比如安装git、vim等等。很麻烦,所以不如直接在宿主机上挂载一个目录到容器中去。options -v命令如下:docker run -d \ -v /home/es_config/plugins:/usr/share/elasticsearch/plugins \ -p 0.0.0.0:9200:9200 \ -p 0
2021-01-21 10:02:25 1596
原创 Docker安装elasticsearch及遇到的问题
先给一行命令docker run -d -p 9200:9200 -p 9300:9300 -e "ES_JAVA_OPTS=-Xms512m -Xmx512m" --name=<your es name> elasticsearch:<es version>使用该命令可直接安装并运行es的docker 镜像容器问题使用命令docker run -d -p 9200:9200 -p 9300:9300 --name=<your es name> elastics
2021-01-20 10:45:54 183
原创 ElasticSearch API介绍及使用
工具使用的是postman新建索引库PUT http://localhost:9200/<你的索引库名称>请求:响应:在索引库中新建分类和文档POST http://localhost:9200/<你的索引库名称>/<要新建的分类名称>请求:响应:查询所有文档GET http://localhost:9200/<你要查询的索引库>/<你要查询的分类>/_search请求:响应:根据id查询文档.
2021-01-20 10:44:50 154
原创 引入Spring Data Redis
需要使用到的pom包<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-redis</artifactId></dependency>当然肯定你是默认使用的Spring boot 2.x项目配置spring: datasource: red..
2021-01-20 10:41:12 124
原创 搭建nexus3遇到的问题
tensquarethis is tensquare一个类似csdn的东西nexus3的坑搭建好nexus3后,配置了~/.m2/settings.xml文件,和项目中的pom.xml文件。如下settings.xml<?xml version="1.0" encoding="utf-8"?><settings> <servers> <!-- 这是公司的maven nexus 用户名密码 --> <
2021-01-20 10:38:51 313
原创 使用Socket&反射&Java流操作进行方法的远程调用(模拟RPC远程调用)
写在前面阅读本文首先得具备基本的Socket、反射、Java流操作的基本API使用知识;否则本文你可能看不懂。。。服务端的端口监听进行远程调用,那就必须得有客户端和服务端。服务端负责提供服务,客户端来对服务端进行方法调用。所以现在我们清楚了: 需要一个服务端、一个客户端那么我们说干就干,我们先建立一个服务端:通过Socket监听本地服务器的一个端口(8081)调用socket的accept方法等待客户端的连接(accpet方法原理)/** * RPC服务端 * @author w
2021-01-20 10:30:49 123
原创 设计模式之代理模式(下) CGLIB动态代理
CGLIB动态代理CGLIB动态代理非常强大、性能还挺厉害(点这里查看JDK与CGLIB的性能对比(引用))。它的主要原理是:CGLIB通过字节码技术动态的生成业务类的子类,覆盖业务类的方法。并进行代理,因为采用的是继承方式,所以无法使用对final修饰的类进行代理。光看原理肯定还是不是那么了解的,所以我们还是来写代码吧!首先编写一个业务类/** * 人员信息服务 * @author wushuaiping * @date 2018/3/14 下午10:44 */public c
2021-01-20 10:29:51 98
原创 设计模式之代理模式(上) 静态代理与JDK动态代理
代理模式给某一个对象提供一个代理,并由代理对象控制对原对象的引用。静态代理静态代理是由我们编写好的类,在程序运行之前就已经编译好的的类,此时就叫静态代理。说理论还是比较懵逼的,直接上代码:抽象主题,可以想象成我们的业务接口。/** * 抽象主题。 * @author wushuaiping * @date 2018/3/13 下午10:13 */public interface ISubject { /** * 比如现在有个业务功能,需要开启某项校验。
2021-01-20 10:29:04 58
原创 设计模式之工厂模式
工厂模式告诉工厂类,我需要什么,工厂类就会为我提供什么;工厂模式就是典型的面向接口编程,最大化的降低了编码的耦合性。简单工厂模式简单工厂模式比较简单,也是项目中可能会经常用到的一种设计模式。比如,我们在开发时,我们会有不同的库,比如:线下开发环境数据库,预发环境数据库,生产环境数据库。如果不通过工厂模式,我们每次切换环境时,都需要手动改动相关的数据库连接代码,此时代码就产生了严重的耦合。而我们使用简单工厂模式,就可以极大的降低这种耦合,编写的代码如下:定义一个连接数据库的接口/** *
2021-01-20 10:27:29 65
原创 设计模式之单例模式
单例模式只有一个实例;必须由自己创建自己的唯一实例;必须提供一个公共方法供其他对象使用自己的实例。饿汉式单例模式饿汉式顾名思义,不管你需不需要,只要你引用了该类,就会创建对象的实例。 * 经典的饿汉式单例模式 * [@author](https://my.oschina.net/arthor) wushuaiping * [@date](https://my.oschina.net/u/2504391) 2018/3/10 上午9:17 */public class Singlet
2021-01-20 10:26:33 69
空空如也
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人