不二人生
刀光剑影江湖情,摧枯拉朽浪滔滔。功名利禄拂衣去,山高水远路迢迢。一个上得了厅堂下得了厨房、左手写诗右手写词的男人
展开
-
Java集合汇总篇
一. 集合框架Java 集合框架一些列的接口和类来实现很多常见的数据结构和算法,例如 LinkedList 就是集合框架提供的实现了双向链表的数据结构,关于这一篇文章建议大家收藏,我会不断地完善和扩充它的内容,例如最下面的系列文章我以后也会对它进行不断的更新集合框架的接口集合框架提供了很多接口,这些接口都包含了特定的方法来实现对集合上的特定操作)我们将要学习这些接口以及子接口和它们的各种实现类,在开始之前我们先简单学习一下这些广泛运用的接口,可以看到整个集合框架,总共有三个顶级接口Collecti原创 2020-12-13 20:25:05 · 186290 阅读 · 3 评论 -
深度剖析JavaOptional类
Optional 虽然可以帮助我们避免NullPointerException,但是这不是绝对的,有的时候即使我们使用了Optional,但是也要注意我们使用的方式,也就是要注意使用Optional提供的方法,避免写出类似的大量空值检测的方法。原创 2023-03-09 21:10:13 · 37241 阅读 · 0 评论 -
深度剖析Java集合之Properties
Properties 在我们写代码中还是比较常用的,所以我们知道有这个东西就行了,在我们需要一些配置选项的时候就可以使用Properties 来完成需求。原创 2023-02-27 14:04:52 · 36850 阅读 · 0 评论 -
Java多线程系列—final的各种用法与意义(07)
finalfinal 是 Java 中的一个关键字,简而言之,final 的作用意味着“这是无法改变的”。不过由于 final 关键字一共有三种用法,它可以用来修饰变量、方法或者类,而且在修饰不同的地方时,效果、含义和侧重点也会有所不同,所以我们需要把这三种情况分开介绍。final 修饰变量关键字 final 修饰变量的作用是很明确的,那就是意味着这个变量一旦被赋值就不能被修改了,也就是说只能被赋值一次,直到天涯海角也不会“变心”。如果我们尝试对一个已经赋值过 final 的变量再次赋值,就会报编译原创 2021-06-16 18:20:39 · 60748 阅读 · 1 评论 -
Java多线程系列—线程安全问题(06)
线程安全问题什么是线程安全要想弄清楚线程安全问题,首先需要了解什么是线程安全,线程安全经常在工作中被提到,比如:你的对象不是线程安全的,你的线程发生了安全错误,虽然线程安全经常被提到,但我们可能对线程安全并没有一个明确的定义。《Java Concurrency In Practice》的作者 Brian Goetz 对线程安全是这样理解的,当多个线程访问一个对象时,如果不用考虑这些线程在运行时环境下的调度和交替执行问题,也不需要进行额外的同步,而调用这个对象的行为都可以获得正确的结果,那这个对象便是线原创 2021-05-05 14:09:35 · 61706 阅读 · 1 评论 -
Java多线程系列—多线程带来的问题(05)
多线程带来的问题为什么需要多线程其实说白了,时代变了,现在的机器都是多核的了,为了榨干机器最后的性能我们引入单线程。为了充分利用CPU资源,为了提高CPU的使用率,采用多线程的方式去同时完成几件事情而不互相干扰,为了处理大量的IO操作时或处理的情况需要花费大量的时间等等,比如:读写文件,视频图像的采集,处理,显示,保存等。性能问题上下文切换Java 中的线程与 CPU 单核执行是一对一的,即单个处理器同一时间只能处理一个线程的执行;而 CPU 是通过时间片算法来执行任务的,不同的线程活跃状态不同原创 2021-05-05 14:08:38 · 62037 阅读 · 1 评论 -
Java多线程系列—生产者消费者模式的多种实现(04)
生产者消费者模式我们先来看看什么是生产者消费者模式,生产者消费者模式是程序设计中非常常见的一种设计模式,被广泛运用在解耦、消息队列等场景。在现实世界中,我们把生产商品的一方称为生产者,把消费商品的一方称为消费者,有时生产者的生产速度特别快,但消费者的消费速度跟不上,俗称“产能过剩”,又或是多个生产者对应多个消费者时,大家可能会手忙脚乱。如何才能让大家更好地配合呢?这时在生产者和消费者之间就需要一个中介来进行调度,于是便诞生了生产者消费者模式。使用生产者消费者模式通常需要在两者之间增加一个阻塞队列作为原创 2021-05-02 12:26:27 · 62373 阅读 · 0 评论 -
Java多线程系列—线程通信机制wait notify notifyAll(03)
线程通信机制wait notify notifyAll本课时我们主要学习 wait/notify/notifyAll 方法的使用注意事项。我们主要从三个问题入手:为什么 wait 方法必须在 synchronized 保护的同步代码中使用?为什么 wait/notify/notifyAll 被定义在 Object 类中,而 sleep 定义在 Thread 类中?wait/notify 和 sleep 方法的异同?wait 必须在 synchronized 保护的同步代码中使用为什么wai原创 2021-05-02 12:25:28 · 61956 阅读 · 0 评论 -
Java多线程系列—线程的运行机制(02)
线程的运行机制在这一节我们主要学习一下线程的启动,线程的停止以及线程的状态流转线程的启动start 方法和 run 方法这个其实是一个非常老生常谈的问题了,就是说我们只有调用start 方法才会帮我们启动一个线程,如果你是直接调用run 方法的话,那其实就是同步调用。public class StartRight { public static void main(String[] args) { Thread t1 = new Thread(() -> {原创 2021-05-01 18:16:31 · 62154 阅读 · 0 评论 -
Java多线程系列—多线程的实现方式(01)
多线程的实现方式实现线程是并发编程中基础中的基础,因为我们必须要先实现线程,才可以继续后续的一系列操作。基本实现方式Runablepublic class ImplementRunable implements Runnable { @Override public void run() { while (true) { // 输出线程的名字,与主线程名称相区分 System.out.println(Thread.cur原创 2021-04-30 14:46:11 · 62388 阅读 · 0 评论 -
Java 线程池初识
文章目录线程池的优势降低资源消耗提升系统响应速度提高线程的可管理性线程池的工作原理任务提交流程图任务提交的流程代码任务的提交方法线程池的关闭线程池创建线程池的参数(7 个)handler 处理策略AbortPolicy策略CallerRunsPolicy策略DiscardOleddestPolicy策略DiscardPolicy策略线程池的参数设计corePoolSizeBlockingQueueThreadPoolExecutor 的意义FixedThreadPoolSingleThreadExecuto原创 2021-04-12 17:50:37 · 62846 阅读 · 0 评论 -
Java时间知多少
java 中的时间在很长的一段时间里,Java 的日期时间解决方案一直是一个备受争议的设计,它的问题很多,有的是概念容易让人混淆(比如:Date 和 Calendar 什么情况下该用哪个),有的是接口设计的不直观(比如:Date 的 setMonth 参数是从 0 到 11),有的是实现容易造成问题(比如:前面提到的 SimpleDateFormat 需要考虑多线程并发的问题,需要每次构建一个新的对象出来)。这种乱象存在了很长时间,有很多人都在尝试解决这个问题(比如 Joda Time)。从 Java原创 2021-03-25 21:40:05 · 63361 阅读 · 2 评论 -
深度剖析Java集合之BitSet
BitSetBitSet类实现了一个按需增长的位向量,实际是由“二进制位”构成的一个Vector。每一位都是一个表示true或者false 的boolean 值。如果我们希望高效地存储这样只有两种类型的数据,就可以使用BitSet。首先需要说明的是,BitSet并不属于集合框架,没有实现List或Map或者Set接口,BitSet更多的表示一种开关信息,对于海量不重复数据,利用索引表示数据的方式,将会大大节省空间使用。位图vector of bits也就是位图,由于可以用非常紧凑的格式来表示给定范原创 2021-01-24 19:50:39 · 64825 阅读 · 0 评论 -
深度剖析Java集合之ArrayDeque
ArrayDequeArrayDeque是Deque接口的一个实现,使用了可变数组,所以没有容量上的限制。同时,ArrayDeque是线程不安全的,在没有外部同步的情况下,不能再多线程环境下使用。ArrayDeque是Deque的实现类,可以作为栈来使用,效率高于Stack;也可以作为队列来使用,效率高于LinkedList。需要注意的是,ArrayDeque不支持null值。ArrayDeque 初识说明书和继承关系还是按照国际惯例,先看一下ArrayDeque 的说明书,其实往往很多时候你的困原创 2021-01-23 11:22:26 · 64953 阅读 · 1 评论 -
深度剖析Java集合之LinkedDeque
LinkedDeque前面我们学习了Queue,在Java 中的实现其实就是LinkedList,我们的使用方式就是Queue<Integer> numbers = new LinkedList<>();通过声明一个Queue接口窄化了对LinkedList的方法的访问权限,使得对象的使用更像是一个队列而不是一个原生的LinkedList我们发现LinkedList可以当做Queue使用那是因为LinkedList 实现了Queue接口,但是我们从上面的实现中注意到另外一个问题原创 2021-01-20 20:58:59 · 64680 阅读 · 1 评论 -
深度剖析Java集合之LinkedQueue
前面我们学习了Stack,学习了ArrayList ,学习了Vector,**其实Vector和ArrayList一样,都是基于数组实现的List,也就是说都是属于List 阵营的,其主要的区别是在于线程安全上**,二者的底层实现都是基于数组的,stack 集合实现了数据结构Stack 的定义,底层依赖Vector 实现也就是数组,**对栈顶元素的操作实际上是对数组尾部元素的操作**,因为这样可以避免数据的迁移。也就是说我们是用数组实现的Stack,今天我们学习一个和Stack同样重要的数据结构Queu原创 2021-01-20 14:05:26 · 64964 阅读 · 0 评论 -
深度剖析Java集合之EnumSet
EnumSet 是一个用来存储枚举常量的集合,其底层是通过位向量实现的,所以有比较好的一个性能。原创 2021-01-17 20:01:18 · 64510 阅读 · 0 评论 -
深度剖析Java集合之EnumMap
1. 首先我们得清楚EnumMap的使用场景,其次我们得知道EnumMap能实现的HashMap 都能实现,因为EnumMap是一种特殊的Map2. EnumMap的性能更好,这是因为EnumMap的Enum特性决定了不论是从设计上,实现上,存储上都决定了其有很好的性能3. EnumMap还有其特殊的一些特性,例如维持了自然顺序。原创 2021-01-17 12:02:10 · 65303 阅读 · 0 评论 -
Java数据类型—BigDecimal
1. 当我们在进行有着高精度的计算要求的时候不要使用double和float 因为它们有着精度丢失的问题2. 如果使用BigDecimal的时候,不要选择double值作为初始化的值,因为它同样会引入精度的问题3. 如果你使用BigDecimal时候设置了精度,那就同时提供舍入模式,告诉BigDecimal如何舍入从而提供你想要的精度4. BigDecimal继承了Number类和实现了Comparable接口5. BigDecimal 针对加减乘除提供可特定的方法,因为BigDecimal不支持原创 2021-01-16 19:23:38 · 64188 阅读 · 0 评论 -
集合工具类Arrays深度剖析
1. 关于数组的拷贝底层调用的是 System.arraycopy,所以我们除了使用Arrays工具类提供的两个拷贝方法,也可以使用System.arraycopy 方法2. List、Set 等这些集合类在Java中提供了很多可以操作方法,但是数组它是不属于集合体系下的,它是通过`[]` 进行标识的,它没有提供给用户可操作的任何方法,只提供了一个`length` 属性,所以Arrays工具类提供了很多的方法可以方便的让我们操作数组原创 2021-01-16 16:58:11 · 63388 阅读 · 0 评论 -
集合工具类Collections深度解析
本文主要介绍Collections的常用方法,例如 Collections.sort()、Collections.shuffle()、Collections.reverse()、Collections.addAll()、Collections.copy()、Collections.binarySearch()、Collections.synchronizedXXX()还有就是针对Collections.copy() 的方式源码进行讲解,从而避免`IndexOutOfBoundsException: So原创 2020-12-03 21:30:18 · 30587 阅读 · 2 评论 -
Java数据类型—String扩展
String 扩展方法Join方法 让代码更优美有时候我们会遇到将一个集合里面的字符串使用特定的分隔符进行拼接,这个时候我们可以使用join 方法,一方面是性能,一方面是代码简洁 @Test public void join(){ String[] text = {"hello", "word","are","you","ok","?"}; System.out.println(String.join(",", text)); List&l原创 2020-12-26 11:12:02 · 51682 阅读 · 0 评论 -
Java数据类型—StringBuilder与StringBuffer
StringBuilder与StringBuffer作用就是用来处理字符串,但String类本身也具备很多方法可以用来处理字符串,那么为什么还要引入这两个类呢?前面我们讲解到String 对象的不可变性,以及它的不足那就是创建新的对象,因为它是不可变的,所以你对它的操作逻辑就体现在另外一个对象里,那就是你的操作新创建的对象。...原创 2020-12-22 20:24:28 · 44882 阅读 · 2 评论 -
Java数据类型—String进阶之不可变性
1. 不可变性的实现方式2. 为什么需要不可变性或者说是不可变性的好处3. 不可变性的不足以及改进方案原创 2020-12-20 11:58:21 · 43952 阅读 · 1 评论 -
Java数据类型—String进阶之字符串常量池
作为最基础用的最多的引用数据类型,Java 设计者为String 提供了各种优化,其中就有为 String 提供了字符串常量池以提高其性能,主要就是为了降低内存开销,那么字符串常量池的具体原理是什么,我们带着以下三个问题,去理解字符串常量池原创 2020-12-20 10:53:30 · 44309 阅读 · 3 评论 -
Java数据类型—String基础
1. Java 语言针对字符串的拼接和将其他对象转化成字符串提供了特殊的支持2. Java为了优化字符串的性能,提供了字符串常量池3. String 不可变的原因是底层存储的字节数组是final 修饰的和String 类是被final 修饰的原创 2020-12-17 14:25:26 · 42236 阅读 · 4 评论 -
Java枚举—枚举初识
1. **枚举的好处**:可以将常量组织起来,统一进行管理 枚举的典型应用场景 **错误码、状态机等**。2. 枚举的使用方法很简单,只需要使用enum 关键字申明即可3. 枚举的底层原理是继承了Enum 抽象类,编译器最终会将枚举编译成一个普通的Java类供Java 虚拟机使用4. 枚举中申明的变量都是有类型的,那就是该枚举类型(其实也是一个普通的java类)原创 2020-12-15 16:26:21 · 41981 阅读 · 3 评论 -
Java枚举—枚举进阶
上一节我们讲了[枚举初识]里面主要讲了枚举的实现原理,我们从编译器的角度看了枚举的底层实现以及枚举常用的方法今天我们看一下枚举添加自定义方法和构造函数,枚举的抽象和接口,枚举与switch 和基于枚举的单例,之后我们会讲解两个和枚举相关的数据结构EnumMap 和EnumSet原创 2020-12-16 11:13:52 · 41775 阅读 · 5 评论 -
胡说八道JVM—java虚拟机概论
虚拟机是一个相对于 “物理机”的概念,这两种机器都有代码执行能力,其区别是物理机的执行引擎是直接建立在处理器、硬件、指令集和操作系统层面上的,而虚拟机的执行引擎则是由自己实现的,因此可以自行制定指令集与执行引擎的结构体系,并且能够执行哪些不被硬件直接支持的指令集格式。原创 2020-12-14 22:28:34 · 41382 阅读 · 1 评论 -
胡说八道JVM—运行时数据区(栈)
虚拟机栈是Java执行方法的内存模型。每个方法被执行的时候,都会创建一个栈帧,把栈帧压人栈,当方法正常返回或者抛出未捕获的异常时,栈帧就会出栈。然后又将栈内存分为pc寄存器、本地方法栈、Java方法栈需要注意的是,在jvm规范中运行时数据区包括,栈和本地方法栈,但是对于本地方法栈的实现没有严格的约束,所以hotspot 虚拟机将本地方法栈和虚拟机栈合二为一原创 2020-12-14 22:22:27 · 41300 阅读 · 0 评论 -
深度剖析Java集合之Stack
Java 集合框架提供了一个集合Stack,它提供了stack 数据结构的功能stack 集合实现了数据结构Stack 的定义,底层依赖Vector 实现也就是数组,对栈顶元素的操作实际上是对数组尾部元素的操作,因为这样可以避免数据的迁移原创 2020-12-13 13:24:19 · 42869 阅读 · 0 评论 -
深度剖析Java集合之TreeSet
HashMap 增加了双向链表维持了顺序,HashSet使用了HashMap弱化了Key-Value 中的Value 实现了去重且只有value集合的功能,LinkedHashSet 则是使用了LinkedHashMap,那么TreeSet 呢,也是使用了TreeMap 吗,其实就是的,学完本文你就知道了原创 2020-12-10 19:57:32 · 42594 阅读 · 0 评论 -
深度剖析Java集合之TreeMap
之前 LinkedHashMap那篇文章里提到过了,HashMap 是无序的,所有有了 LinkedHashMap,加上了双向链表后,就可以保持元素的插入顺序或者访问顺序,那 TreeMap 呢,TreeMap 由红黑树实现,可以保持元素的自然顺序,这里指的是实现了 Comparable 接口的自然排序,或者是由Comparator定义的自定义排序原创 2020-12-10 11:14:36 · 42637 阅读 · 0 评论 -
一文掌握Comparator的数十种用法
一文掌握Comparator的数十种用法,nullsFirst 和 nullsLast 方法,comparing方法的两种形式,Comparator.naturalOrder 和 Comparator.reverseOrder的原理原创 2020-12-09 21:33:59 · 42624 阅读 · 0 评论 -
深度剖析—Comparable和Comparator
1. 需要被排序的对象实现Comparable 接口,所以可以认为比较的属性是对象本身已经有了的,所以我们将由Comparable 实现的排序叫做自然排序2. 当Comparable 实现的排序不能满足需求的时候,你可以使用Comparator 进行排序,这个往往是因为需要排序的对象的类的定义已经存在的时候(或者说是这个类不是你定义的)3. 有时候我们可以使用Comparator 提供的两个方法来改变Comparable的排序类型,或者说是排序方向原创 2020-12-09 21:25:18 · 41665 阅读 · 4 评论 -
深度剖析Java集合之Vector
其实Vector和ArrayList一样,都是基于数组实现的List,也就是说都是属于List 阵营的,其主要的区别是在于线程安全上,二者的底层实现都是基于数组的Vector 实现线程安全的方式就是给方法上加synchronized 锁,**所以线程安全的情况下请使用ArrayList,多线程的情况下使用Vector**,Vector 在目前的开发中也用的不多,主要是它实现线程安全的方式比较低效,但是如果有一天Java 将synchronized锁的效率提高了,那Vector依然是一个不错的选择原创 2020-12-08 20:32:56 · 43909 阅读 · 0 评论 -
深度剖析—LinkedList
LinkedList和ArrayList一样是集合List的实现类,虽然较之ArrayList,其使用场景并不多,但同样有用到的时候,那么接下来,我们来认识一下它。其实它们两个都同属于List阵营,只不过实现方式有所差异,ArrayList 就是借助Array 实现的List,LinkedList 就是借助双向链表(Linked) 实现的List原创 2020-12-06 20:38:47 · 43284 阅读 · 3 评论 -
深度剖析LinkedHashSet
HashMap 是一个利用数组存储key-value键值对的一个数据结构,为了有序的要求,然后我们引入了LinkedHashMap来满足我们对顺序的要求,再到后面我们学习了HashSet这种数据结构,利用的是HashMap的Key 的唯一性来实现HashSet 的去重的目的LinkedHashSet 也HashSet 一样也在内部使用了HashMap,因为LinkedHashSet要维持元素之间的顺序,所以它使用的实HashMap的有序版本,也就是LinkedHashMap原创 2020-12-05 17:15:57 · 46494 阅读 · 0 评论 -
深度剖析HashSet
HashSet是Java集合Set的一个实现类,Set是一个接口,其实现类除HashSet之外,还有TreeSet,并继承了Collection,HashSet集合很常用,同时也是程序员面试时经常会被问到的知识点我就没见过这么不要脸的数据结构,还给自己起名 HashSet 搞得跟 HashMap 是同一级别上的,对外糊弄用户,对内欺骗HashMap,每次value 都给人一不变的数据这不跟蛋壳一样了吗,一刀双割...原创 2020-12-05 13:02:29 · 42556 阅读 · 0 评论 -
深度剖析ArrayList
ArrayList是集合的一种实现,实现了接口List,List接口继承了Collection接口。ArrayList 是java 中最常用的集合类型,这是因为它使用起来非常简单,而且它提供了非常丰富的功能,并且性能非常好,这里需要注意的是性能是以牺牲了线程安全为代价的,ArrayList 好用又很大一部分来自它的动态扩容,不像数组那样你需要提前计算好数组的大小,ArrayList 会随着元素的增加自动扩容。原创 2020-12-05 09:29:10 · 44898 阅读 · 3 评论