
java基础
马彼得
平常心
展开
-
List--方法内的list传递给入参后方法外获取不到的原因和解决办法
我们经常使用List来做数据集合存放数据,经常使用时我们知道list是可以实现地址传递,也就是在list通过方法的入参传递到方法内后,整个list的值可以在方法内使用:通过add方法可以在原来的基础上增加新值,也可以通过set(index,值)的方式改变原来index位置的数据而且入参传递的值经过add、set等后再方法外也是生效的,就是这个操作后的值,这就是地址传递,也就是对象传递。但是,我们容易忽略的一点儿是:当在方法内发生新的list整体赋值给入参的list的时候(例如例子里的st转载 2020-12-03 20:17:28 · 1887 阅读 · 0 评论 -
BufferedInputStream和FileInputStream的区别
BufferedInputStream是带缓冲区的输入流,默认缓冲区大小是8M,能够减少访问磁盘的次数,提高文件读取性能;BufferedOutputStream是带缓冲区的输出流,能够提高文件的写入效率。BufferedInputStream与BufferedOutputStream分别是FilterInputStream类和FilterOutputStream类的子类,实现了装饰设计模式。当传输的文件特别大的时候,BufferInputStream的优点就体现出来了 ,不带缓冲的操作(FilterI转载 2020-08-27 13:40:48 · 1155 阅读 · 1 评论 -
Java中try()catch{}的使用方法用法
在看Zookeeper源码的时候,偶尔看到的一个关于try()...catch()的用法,通常我们使用try...catch()捕获异常的,如果遇到类似IO流的处理,要在finally部分关闭IO流,当然这个是JDK1.7之前的写法了;在JDK7优化后的try-with-resource语句,该语句确保了每个资源,在语句结束时关闭。所谓的资源是指在程序完成后,必须关闭的流对象。写在()里面的流对象对应的类都实现了自动关闭接口:AutoCloseable;格式:try (创建流对象语句,如果多个,使原创 2020-08-24 22:53:35 · 4738 阅读 · 2 评论 -
java基础:基本类型占用字节数
1.整型类型 存储需求 bit数 取值范围 备注int 4字节 4*8short 2字节 2*8 -32768~32767long 8字节 8*8byte 1字节 1*8 -128~1272.浮点型类型 ...原创 2020-08-23 21:27:01 · 192 阅读 · 0 评论 -
Java中switch支持字符串原理
Java7之后的版本才开始支持switch字符串,但是内部实现case还是基于整形变量的匹配。下面编写一个使用switch字符串的sample来看下。package org.sun.sample.pojo;/** * Created by aron on 16-4-11. */public class SwitchSample { public static final String RED= "RED"; public static final String BLUE=转载 2020-05-21 21:51:13 · 1565 阅读 · 0 评论 -
深入理解happens-before规则
为什么会有happens-before 规则?因为jvm会对代码进行编译优化,指令会出现重排序的情况,为了避免编译优化对并发编程安全性的影响,需要happens-before规则定义一些禁止编译优化的场景,保证并发编程的正确性。public class VolatileExample { int x = 0 ; volatile boolean v = false; ...原创 2020-05-13 00:30:03 · 298 阅读 · 0 评论 -
ConcurrentHashMap的transfer
扩容是ConcurrentHashMap的精华之一,扩容操作的核心在于数据的转移,在单线程环境下数据的转移很简单,无非就是把旧数组中的数据迁移到新的数组。但是这在多线程环境下,在扩容的时候其他线程也可能正在添加元素,这时又触发了扩容怎么办?可能大家想到的第一个解决方案是加互斥锁,把转移过程锁住,虽然是可行的解决方案,但是会带来较大的性能开销。因为互斥锁会导致所有访问临界区的线程陷入到阻塞状态,持有...转载 2020-05-07 15:03:08 · 3264 阅读 · 3 评论 -
ConcurrentHashmap的addCount(2)
判断是否需要扩容,也就是当更新后的键值对总数baseCount >= 阈值sizeCtl时,进行rehash,这里面会有两个逻辑。/** * 在putVal最后调用addCount的时候,传递了两个参数,分别是1和binCount(链表长度) * x表示这次需要在表中增加的元素个数,check参数表示是否需要进行扩容检查,大于等于0都需要进行检查 */private fin...转载 2020-05-07 11:25:52 · 464 阅读 · 2 评论 -
ConcurrentHashmap的fullAddCount
fullAddCount主要是用来初始化CounterCell,来记录元素个数,里面包含扩容,初始化等操作private final void fullAddCount(long x, boolean wasUncontended) { int h; //获取当前线程的probe的值,如果值为0,则初始化当前线程的probe的值,probe就是随机数 ...转载 2020-05-06 20:25:33 · 1490 阅读 · 6 评论 -
ConcurrentHashmap的CounterCells
CounterCells解释ConcurrentHashMap是采用CounterCell数组来记录元素个数的,像一般的集合记录集合大小,直接定义一个size的成员变量即可,当出现改变的时候只要更新这个变量就行。为什么ConcurrentHashMap要用这种形式来处理呢? 问题还是处在并发上,ConcurrentHashMap是并发集合,如果用一个成员变量来统计元素个数的话,为了保证并发情况...转载 2020-05-06 20:11:53 · 4569 阅读 · 3 评论 -
ConcurrentHashMap的initTable()
private final Node<K,V>[] initTable() { Node<K,V>[] tab; int sc; while ((tab = table) == null || tab.length == 0) { //被其他线程抢了初始化的操作,则直接让出自己的cpu时间片 ...转载 2020-05-06 18:04:06 · 559 阅读 · 2 评论 -
ConcurrentHashMap的tabAt为什么不用tab[i]
final V putVal(K key, V value, boolean onlyIfAbsent) { if (key == null || value == null) throw new NullPointerException(); int hash = spread(key.hashCode()); int binCount =...转载 2020-05-06 17:51:43 · 1064 阅读 · 0 评论 -
HashTable/ConcurrentHashMap锁力度的区别
HashTable:ConcurrentHashMap:转载 2020-05-06 15:12:32 · 724 阅读 · 0 评论 -
Java中泛型 类型擦除
Java泛型(Generic)的引入加强了参数类型的安全性,减少了类型的转换,但有一点需要注意:Java 的泛型在编译器有效,在运行期被删除,也就是说所有泛型参数类型在编译后都会被清除掉,看下面一个列子,代码如下:public class Foo { public void listMethod(List<String> stringList){ } ...转载 2020-05-02 19:32:06 · 614 阅读 · 0 评论 -
Java中静态代码块、代码块以及构造函数执行顺序详解
在JavaSE的基础笔试题中经常会出现这三个的一个执行顺序,那么他们的执行顺序究竟是怎么样的呢?通过代码我们可以直接看一下最终结果(代码如下)public class testOne extends TestTwo{ public testOne(){ System.out.println("子类构造方法"); } { System.o...转载 2020-05-02 13:05:02 · 189 阅读 · 0 评论 -
java反射机制中class.forName和classloader的区别
一、类加载机制上面两种加载类的方式说到底还是为了加载一个java类,因此需要先对类加载的过程进行一个简单的了解。我们写好的程序,然后run运行,过程可以直接看下面这张图:往细了看大致分为5个阶段:(1)加载:java类运行时候会生成一个class字节码文件,加载的过程就是去我们的操作系统寻找这个class文件。(2)链接:这个过程就是把class文件加载到java虚拟机。(...转载 2020-05-02 13:02:25 · 368 阅读 · 0 评论 -
Hashmap1.7和1.8区别+ConcurrentHashmap1.7和1.8区别
HashmapJDK1.7中使用一个Entry数组来存储数据,用key的hashcode取模来决定key会被放到数组里的位置,如果hashcode相同,或者hashcode取模后的结果相同,那么这些key会被定位到Entry数组的同一个格子里,这些key会形成一个链表;在hash函数特别差的情况下,比如说所有key的hashcode都相同,这个链表可能会很长,那么put/...转载 2020-04-30 15:29:54 · 199 阅读 · 0 评论 -
ConcurrentHashMap的该构造方法
public ConcurrentHashMap(int initialCapacity) // 校验初始容量不能小于0 if (initialCapacity < 0) throw new IllegalArgumentException(); int cap = ((initialCapacity >= (MAXIMUM_CAPACITY...原创 2020-04-30 14:52:42 · 556 阅读 · 0 评论 -
HashMap的最大容量为什么是2的30次方?
今天看HashMap的底层实现,发现HashMap的最大容量规定为:// 最大容量(必须是2的幂且小于2的30次方,传入容量过大将被这个值替换)static final int MAXIMUM_CAPACITY = 1 << 30;当看到 1<<30 时,对“<<” 有点模糊,当了解“<<”的用法之后,又有一个问题;int类型不是4个...转载 2020-04-30 14:27:02 · 698 阅读 · 1 评论 -
Java HashSet工作原理及实现
HashSet是基于HashMap来实现的,操作很简单,更像是对HashMap做了一次“封装”,而且只使用了HashMap的key来实现各种特性,我们先来感性的认识一下这个结构:HashSet<String> set = new HashSet<String>();set.add("语文");set.add("数学");set.add("英语");set.ad...转载 2020-04-23 11:06:33 · 415 阅读 · 1 评论 -
Java范型中 ? extends T 和 ? super T 的区别
前言:向上转型是安全的,向下转型是不安全的,除非你知道List中的真实类型,否则向下转型就会报错。extendsList<? extends Number> foo3意味着下面的赋值语句都是合法的:List<? extends Number> foo3 = new ArrayList<Number>(); // Number "extends" ...转载 2020-02-28 22:48:13 · 234 阅读 · 1 评论 -
对象传入方法内然后赋值成null,为什么执行完方法之后,值不是null?
因为java只有一种传递参数的方式:值传递。在值传递中,实参的值被传给形参,方法体内对形参的任何赋值操作都不会影响到实参。因为java只有一种传递参数的方式:值传递。在值传递中,实参的值被传给形参,方法体内对形参的任何赋值操作都不会影响到实参。那第二个图,修改了形参的属性值,为什么形参就会把实参属性值也顺便修改了呢?对形参的任何赋值操作都不会影响到实参,但是对于形参...转载 2020-02-07 22:07:49 · 1702 阅读 · 0 评论 -
匿名内部类访问的局部变量为什么必须要用final修饰
我们先来看一段代码: public class Hello { public static void main(String[] args) { String str="haha"; new Thread() { @Override public void run() { System.out.println(str); } }.start(); ...转载 2019-12-03 14:29:01 · 1975 阅读 · 0 评论 -
抽象类通过子类被实例化
抽象类其实是可以被实例化的,但是它的实例化方式并不是通过普通的new方式来创建对象,而是通过父类的应用来指向子类的实例间接地实现父类的实例化,因为子类在实例化之前,一定会先实例化它的父类。这样创建了继承抽象类的子类对象,也就把其父类(抽象类)给实例化了。注意:接口与抽象类非常类似,但是它不可以被实例化,因为接口压根没有构造函数。public abstract class B { ...原创 2019-12-03 13:50:00 · 4478 阅读 · 0 评论 -
要先确保对象重写equals()和hashCode()方法
当新建一个java类时,需要重写equals和hashcode方法,大家都知道!但是,为什么要重写呢?需要保证对象调用equals方法为true时,hashcode必须相同.先看下面的例子:没有重写equals和hashcode方法User类public class User { private Integer age; private String name; p...转载 2019-03-01 11:11:40 · 152 阅读 · 0 评论 -
为什么要重写java中对象的equals方法和hashCode方法以及如何重写
当我们写了一个类的时候,我们一般要重写这个类的equals方法,因为所有类都继承Object,而Object中的equals方法是这么写的:public boolean equals(Object obj){ return this==obj;}也就是Object中的equals方法实际上比较的是两个对象是否是同一个(包含内存地址的相等),显然当我们只想比较两个对象的数值是否相...转载 2019-03-01 10:44:06 · 163 阅读 · 0 评论 -
BIO通信的弊端
Netty是一个高性能、异步事件驱动的NIO框架,它提供了对TCP、UDP和文件传输的支持,作为一个异步NIO框架,Netty的所有IO操作都是异步非阻塞的,通过Future-Listener机制,用户可以方便的主动获取或者通过通知机制获得IO操作结果。作为当前最流行的NIO框架,Netty在互联网领域、大数据分布式计算领域、游戏行业、通信行业等获得了广泛的应用,一些业界著名的开源组件也基于N...翻译 2018-08-19 14:47:39 · 540 阅读 · 0 评论 -
深入详解HashSet的元素为什么要重写hashCode和equals方法
在Object这个类中hashCode是本地方法,它的值与对象在内存中的地址有关,所以不会存在两个hashCode返回值相同的对象,equals是比较对象的引用是否相等hashCode方法的目的是什么呢?—它是为hash table中插入为提供hash数值HashSet:一个是无序不重复的集合,你知道为什么吗?因为HashSet根据hashCode返回值和equals来判断两个对象...转载 2019-03-01 11:17:41 · 2333 阅读 · 3 评论 -
HashSet的实现原理去重
/*集合 的体系:------------| Collection 单例集合的根接口----------------| List 如果是实现了List接口的集合类,具备的特点: 有序,可重复。-------------------| ArrayList ArrayList 底层是维护了一个Object数组实现的。 特点: 查询速度快,增删慢。-------------------...原创 2019-03-01 14:10:03 · 1789 阅读 · 0 评论 -
Java规则之条件语句中||常犯的错误
在Java中,逻辑运算符||(短路或)具体运算规则如下:||的运算规则:i.当符号左边表达式为true时,||将直接返回true不在判断符号右边的表达式结果。ii.当符号左边表达式为false时,将继续判断符号右边表达式,||的结果与右边表达式结果一致。根据&&和||的运算规则,下面我们来对以上错误实例进行分析。...原创 2019-02-27 00:13:42 · 293 阅读 · 0 评论 -
final基本数据类型 VS final引用数据类型
如果final修饰的是一个基本数据类型的数据,一旦赋值后就不能再次更改,那么,如果final是引用数据类型了?这个引用的对象能够改变吗?我们同样来看一段代码。public class FinalExample { //在声明final实例成员变量时进行赋值 private final static Person person = new Person(24, 170); ...转载 2019-06-05 14:46:08 · 1823 阅读 · 0 评论 -
Java之泛型<T> T与T的用法
<T> T表示返回值是一个泛型,传递啥,就返回啥类型的数据,而单独的T就是表示限制你传递的参数类型,这个案例中,通过一个泛型的返回方式,获取每一个集合中的第一个数据, 通过返回值<T> T和T的两种方法实现<T> T用法这个<T> T表示的是返回值T是泛型,T是一个占位符,用来告诉编译器,这个东西先给我留着,等我编译的时候,告诉你。...转载 2019-06-04 15:44:45 · 1093 阅读 · 0 评论 -
Java重写ToString()方法的意义
1、为什么要重写ToString?其实对于一般的对象来说都会有这个方法,这个方法的目的,主要就是将对象按字符串的方式输出出来,用白话说就是:使用文字描述这个对象里各个变量是什么值 ,这个变量是什么类型的变量等 ,并且任何类都从Object继承了这个方法,你不重写toString()方法的话输出的就是一个内存地址,也就是哈希码值。并不是输出这个类的各个变量的值,记得不重写好像只打印...转载 2020-02-23 23:14:52 · 5059 阅读 · 4 评论 -
Java中final、finally、finalize的区别与用法
1.简单区别:final用于声明属性,方法和类,分别表示属性不可交变,方法不可覆盖,类不可继承。finally是异常处理语句结构的一部分,表示总是执行。finalize是Object类的一个方法,在垃圾收集器执行的时候会调用被回收对象的此方法,供垃圾收集时的其他资源回收,例如关闭文件等。2.中等区别:虽然这个单词在Java中都存在,但是并没太多关联:final:java中的关键字,修饰符...转载 2019-02-28 21:22:58 · 396 阅读 · 0 评论 -
常见的与内部类相关的笔试面试题
1.根据注释填写(1),(2),(3)处的代码public class Test{ public static void main(String[] args){ // 初始化Bean1 (1) bean1.I++; // 初始化Bean2 (2) be...转载 2019-02-13 17:48:42 · 242 阅读 · 0 评论 -
JAVA中HashMap扩容机制
第一部分:HashMap<String, String> hmap=new HashMap<>();HashSet<String> hset=new HashSet<>();Hashtable<String, String> htable=new Hashtable<>();1. HashMap扩容 HashM...翻译 2018-11-24 16:05:07 · 852 阅读 · 0 评论 -
Java中的i++、++i语句
在几乎所有的命令式编程语言中,必然都会有i++和++i这种语法。在编程启蒙教材《C语言程序设计》一书中,也专门解释了这两条语句的区别。有些语言中i++和++i既可以作为左值又可以作为右值,笔者专门测试了一下,在Java语言中,这两条语句都只能作为右值,而不能作为左值。同时,它们都可以作为独立的一条指令执行。int i = 0;int j1 = i++; // 正确int j2 = ++i...转载 2018-10-04 22:49:46 · 207 阅读 · 0 评论 -
ArrayList的底层实现原理
一、对于ArrayList需要掌握的七点内容ArrayList的创建:即构造器 往ArrayList中添加对象:即add(E)方法 获取ArrayList中的单个对象:即get(int index)方法 删除ArrayList中的对象:即remove(E)方法 遍历ArrayList中的对象:即iterator,在实际中更常用的是增强型的for循环去做遍历 判断对象是否存在于Arra...转载 2018-09-19 20:12:09 · 315 阅读 · 1 评论 -
HashSet、HashMap、ArrayList、LinkedList、Vector区别
什么是HashSetHashSet实现了Set接口,它不允许集合中有重复的值,当我们提到HashSet时,第一件事情就是在将对象存储在HashSet之前,要先确保对象重写equals()和hashCode()方法,这样才能比较对象的值是否相等,以确保set中没有储存相等的对象。如果我们没有重写这两个方法,将会使用这个方法的默认实现。public boolean add(Object o)方...翻译 2018-09-19 11:19:25 · 300 阅读 · 0 评论 -
一致性哈希算法
使用场景现在我们假设有100台redis data服务器,一份数据101进来的时候,以散列公式hash(i)&100,计算所存放的服务器,假设hash(i) = i,那么数据被散列到标号为1的服务器,然后这个时候服务器新增了一台,然后散列公式为hash(i)%101,这个时候请求访问数据101的时候,被分配至0号服务器,但是其实这个时候数据是在1号服务器的。所以这个时候大量的数据失...翻译 2018-09-09 17:48:55 · 194 阅读 · 0 评论