This commit is contained in:
CyC2018 2019-03-27 20:47:23 +08:00
commit e6fa0a5afe
6 changed files with 313 additions and 1 deletions

View File

@ -1,3 +1,4 @@
<<<<<<< HEAD
# 一、数据类型 # 一、数据类型
## 基本类型 ## 基本类型
@ -17,6 +18,69 @@ boolean 只有两个值true、false可以使用 1 bit 来存储
- [The Java® Virtual Machine Specification](https://docs.oracle.com/javase/specs/jvms/se8/jvms8.pdf) - [The Java® Virtual Machine Specification](https://docs.oracle.com/javase/specs/jvms/se8/jvms8.pdf)
## 包装类型 ## 包装类型
=======
<!-- GFM-TOC -->
* [一、数据类型](#一数据类型)
* [基本类型](#基本类型)
* [包装类型](#包装类型)
* [缓存池](#缓存池)
* [二、String](#二string)
* [概览](#概览)
* [不可变的好处](#不可变的好处)
* [String, StringBuffer and StringBuilder](#string,-stringbuffer-and-stringbuilder)
* [String Pool](#string-pool)
* [new String("abc")](#new-string"abc")
* [三、运算](#三运算)
* [参数传递](#参数传递)
* [float 与 double](#float-与-double)
* [隐式类型转换](#隐式类型转换)
* [switch](#switch)
* [四、继承](#四继承)
* [访问权限](#访问权限)
* [抽象类与接口](#抽象类与接口)
* [super](#super)
* [重写与重载](#重写与重载)
* [五、Object 通用方法](#五object-通用方法)
* [概览](#概览)
* [equals()](#equals)
* [hashCode()](#hashcode)
* [toString()](#tostring)
* [clone()](#clone)
* [六、关键字](#六关键字)
* [final](#final)
* [static](#static)
* [七、反射](#七反射)
* [八、异常](#八异常)
* [九、泛型](#九泛型)
* [十、注解](#十注解)
* [十一、特性](#十一特性)
* [Java 各版本的新特性](#java-各版本的新特性)
* [Java 与 C++ 的区别](#java-与-c-的区别)
* [JRE or JDK](#jre-or-jdk)
* [参考资料](#参考资料)
<!-- GFM-TOC -->
# 一、数据类型
## 基本类型
- byte/8
- char/16
- short/16
- int/32
- float/32
- long/64
- double/64
- boolean/\~
boolean 只有两个值true、false可以使用 1 bit 来存储但是具体大小没有明确规定。JVM 会在编译时期将 boolean 类型的数据转换为 int使用 1 来表示 true0 表示 false。JVM 支持 boolean 数组,但是是通过读写 byte 数组来实现的。
- [Primitive Data Types](https://docs.oracle.com/javase/tutorial/java/nutsandbolts/datatypes.html)
- [The Java® Virtual Machine Specification](https://docs.oracle.com/javase/specs/jvms/se8/jvms8.pdf)
## 包装类型
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
基本类型都有对应的包装类型,基本类型与其对应的包装类型之间的赋值使用自动装箱与拆箱完成。 基本类型都有对应的包装类型,基本类型与其对应的包装类型之间的赋值使用自动装箱与拆箱完成。
@ -626,8 +690,9 @@ SuperExtendExample.func()
存在于继承体系中,指子类实现了一个与父类在方法声明上完全相同的一个方法。 存在于继承体系中,指子类实现了一个与父类在方法声明上完全相同的一个方法。
为了满足里式替换原则,重写有有以下两个限制: 为了满足里式替换原则,重写有以下三个限制:
<<<<<<< HEAD
使用 @Override 注解,可以让编译器帮忙检查是否满足上面的三个限制条件。 使用 @Override 注解,可以让编译器帮忙检查是否满足上面的三个限制条件。
下面的示例中SubClass  SuperClass 的子类SubClass 重写了 SuperClass  func() 方法。其中: 下面的示例中SubClass  SuperClass 的子类SubClass 重写了 SuperClass  func() 方法。其中:
@ -649,6 +714,33 @@ class SubClass extends SuperClass {
    public ArrayList<Integer> func() throws Exception {     public ArrayList<Integer> func() throws Exception {
        return new ArrayList<>();         return new ArrayList<>();
    }     }
=======
- 子类方法的访问权限必须大于等于父类方法;
- 子类方法的返回类型必须是父类方法返回类型或为其子类型。
- 子类方法抛出的异常类型必须是父类抛出异常类型或为其子类型。
使用 @Override 注解,可以让编译器帮忙检查是否满足上面的三个限制条件。
下面的示例中SubClass 为 SuperClass 的子类SubClass 重写了 SuperClass 的 func() 方法。其中:
- 子类方法访问权限为 public大于父类的 protected。
- 子类的返回类型为 ArrayList<Integer>,是父类返回类型 List<Integer> 的子类。
- 子类抛出的异常类型为 Exception是父类抛出异常 Throwable 的子类。
- 子类重写方法使用 @Override 注解,从而让编译器自动检查是否满足限制条件。
```java
class SuperClass {
protected List<Integer> func() throws Throwable {
return new ArrayList<>();
}
}
class SubClass extends SuperClass {
@Override
public ArrayList<Integer> func() throws Exception {
return new ArrayList<>();
}
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
} }
``` ```

View File

@ -1,8 +1,77 @@
<<<<<<< HEAD
# 一、线程状态转换 # 一、线程状态转换
![](index_files/96706658-b3f8-4f32-8eb3-dcb7fc8d5381.jpg) ![](index_files/96706658-b3f8-4f32-8eb3-dcb7fc8d5381.jpg)
## 新建New ## 新建New
=======
<!-- GFM-TOC -->
* [一、线程状态转换](#一线程状态转换)
* [新建New](#新建new)
* [可运行Runnable](#可运行runnable)
* [阻塞Blocking](#阻塞blocking)
* [无限期等待Waiting](#无限期等待waiting)
* [限期等待Timed Waiting](#限期等待timed-waiting)
* [死亡Terminated](#死亡terminated)
* [二、使用线程](#二使用线程)
* [实现 Runnable 接口](#实现-runnable-接口)
* [实现 Callable 接口](#实现-callable-接口)
* [继承 Thread 类](#继承-thread-类)
* [实现接口 VS 继承 Thread](#实现接口-vs-继承-thread)
* [三、基础线程机制](#三基础线程机制)
* [Executor](#executor)
* [Daemon](#daemon)
* [sleep()](#sleep)
* [yield()](#yield)
* [四、中断](#四中断)
* [InterruptedException](#interruptedexception)
* [interrupted()](#interrupted)
* [Executor 的中断操作](#executor-的中断操作)
* [五、互斥同步](#五互斥同步)
* [synchronized](#synchronized)
* [ReentrantLock](#reentrantlock)
* [比较](#比较)
* [使用选择](#使用选择)
* [六、线程之间的协作](#六线程之间的协作)
* [join()](#join)
* [wait() notify() notifyAll()](#wait-notify-notifyall)
* [await() signal() signalAll()](#await-signal-signalall)
* [七、J.U.C - AQS](#七juc---aqs)
* [CountDownLatch](#countdownlatch)
* [CyclicBarrier](#cyclicbarrier)
* [Semaphore](#semaphore)
* [八、J.U.C - 其它组件](#八juc---其它组件)
* [FutureTask](#futuretask)
* [BlockingQueue](#blockingqueue)
* [ForkJoin](#forkjoin)
* [九、线程不安全示例](#九线程不安全示例)
* [十、Java 内存模型](#十java-内存模型)
* [主内存与工作内存](#主内存与工作内存)
* [内存间交互操作](#内存间交互操作)
* [内存模型三大特性](#内存模型三大特性)
* [先行发生原则](#先行发生原则)
* [十一、线程安全](#十一线程安全)
* [不可变](#不可变)
* [互斥同步](#互斥同步)
* [非阻塞同步](#非阻塞同步)
* [无同步方案](#无同步方案)
* [十二、锁优化](#十二锁优化)
* [自旋锁](#自旋锁)
* [锁消除](#锁消除)
* [锁粗化](#锁粗化)
* [轻量级锁](#轻量级锁)
* [偏向锁](#偏向锁)
* [十三、多线程开发良好的实践](#十三多线程开发良好的实践)
* [参考资料](#参考资料)
<!-- GFM-TOC -->
# 一、线程状态转换
<div align="center"> <img src="https://gitee.com/CyC2018/CS-Notes/raw/master/docs/pics/96706658-b3f8-4f32-8eb3-dcb7fc8d5381.jpg"/> </div><br>
## 新建New
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
创建后尚未启动。 创建后尚未启动。
@ -203,7 +272,11 @@ public void run() {
## InterruptedException ## InterruptedException
<<<<<<< HEAD
通过调用一个线程的 interrupt() 来中断该线程如果该线程处于阻塞、限期等待或者无限期等待状态那么就会抛出 InterruptedException从而提前结束该线程。但是不能中断 I/O 阻塞和 synchronized 锁阻塞。 通过调用一个线程的 interrupt() 来中断该线程如果该线程处于阻塞、限期等待或者无限期等待状态那么就会抛出 InterruptedException从而提前结束该线程。但是不能中断 I/O 阻塞和 synchronized 锁阻塞。
=======
通过调用一个线程的 interrupt() 来中断该线程,如果该线程处于阻塞、有限期等待或者无限期等待状态,那么就会抛出 InterruptedException从而提前结束该线程。但是不能中断 I/O 阻塞和 synchronized 锁阻塞。
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
对于以下代码 main() 中启动一个线程之后再中断它由于线程中调用了 Thread.sleep() 方法因此会抛出一个 InterruptedException从而提前结束线程不执行之后的语句。 对于以下代码 main() 中启动一个线程之后再中断它由于线程中调用了 Thread.sleep() 方法因此会抛出一个 InterruptedException从而提前结束线程不执行之后的语句。
@ -1508,7 +1581,19 @@ public static String concatString(String s1, String s2, String s3) {
如果一系列的连续操作都对同一个对象反复加锁和解锁,频繁的加锁操作就会导致性能损耗。 如果一系列的连续操作都对同一个对象反复加锁和解锁,频繁的加锁操作就会导致性能损耗。
<<<<<<< HEAD
上一节的示例代码中连续的 append() 方法就属于这类情况。如果虚拟机探测到由这样的一串零碎的操作都对同一个对象加锁将会把加锁的范围扩展粗化到整个操作序列的外部。对于上一节的示例代码就是扩展到第一个 append() 操作之前直至最后一个 append() 操作之后,这样只需要加锁一次就可以了。 上一节的示例代码中连续的 append() 方法就属于这类情况。如果虚拟机探测到由这样的一串零碎的操作都对同一个对象加锁将会把加锁的范围扩展粗化到整个操作序列的外部。对于上一节的示例代码就是扩展到第一个 append() 操作之前直至最后一个 append() 操作之后,这样只需要加锁一次就可以了。
=======
上一节的示例代码中连续的 append() 方法就属于这类情况。如果虚拟机探测到由这样的一串零碎的操作都对同一个对象加锁,将会把加锁的范围扩展(粗化)到整个操作序列的外部。对于上一节的示例代码就是扩展到第一个 append() 操作之前直至最后一个 append() 操作之后,这样只需要加锁一次就可以了。
## 轻量级锁
JDK 1.6 引入了偏向锁和轻量级锁从而让锁拥有了四个状态无锁状态unlocked、偏向锁状态biased、轻量级锁状态lightweight locked和重量级锁状态inflated
以下是 HotSpot 虚拟机对象头的内存布局,这些数据被称为 Mark Word。其中 tag bits 对应了五个状态,这些状态在右侧的 state 表格中给出。除了 marked for gc 状态,其它四个状态已经在前面介绍过了。
<div align="center"> <img src="https://gitee.com/CyC2018/CS-Notes/raw/master/docs/pics/bb6a49be-00f2-4f27-a0ce-4ed764bc605c.png" width="500"/> </div><br>
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
## 轻量级锁 ## 轻量级锁

View File

@ -216,7 +216,19 @@ obj = null;
- 需要移动大量对象,处理效率比较低。 - 需要移动大量对象,处理效率比较低。
<<<<<<< HEAD
### 3. 复制 ### 3. 复制
=======
优点:
- 不会产生内存碎片
不足:
- 在标记-清除的基础上还需进行对象的移动,成本相对较高
### 3. 复制
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
![](index_files/4_2001550547640585.png) ![](index_files/4_2001550547640585.png)
@ -490,7 +502,11 @@ public static final int value = 123;
初始化阶段才真正开始执行类中定义的 Java 程序代码。初始化阶段是虚拟机执行类构造器 &lt;clinit>() 方法的过程。在准备阶段,类变量已经赋过一次系统要求的初始值,而在初始化阶段,根据程序员通过程序制定的主观计划去初始化类变量和其它资源。 初始化阶段才真正开始执行类中定义的 Java 程序代码。初始化阶段是虚拟机执行类构造器 &lt;clinit>() 方法的过程。在准备阶段,类变量已经赋过一次系统要求的初始值,而在初始化阶段,根据程序员通过程序制定的主观计划去初始化类变量和其它资源。
<<<<<<< HEAD
&lt;clinit>() 是由编译器自动收集类中所有类变量的赋值动作和静态语句块中的语句合并产生的,编译器收集的顺序由语句在源文件中出现的顺序决定。特别注意的是,静态语句块只能访问到定义在它之前的类变量,定义在它之后的类变量只能赋值,不能访问。例如以下代码: &lt;clinit>() 是由编译器自动收集类中所有类变量的赋值动作和静态语句块中的语句合并产生的,编译器收集的顺序由语句在源文件中出现的顺序决定。特别注意的是,静态语句块只能访问到定义在它之前的类变量,定义在它之后的类变量只能赋值,不能访问。例如以下代码:
=======
&lt;clinit>() 是由编译器自动收集类中所有类变量的赋值动作和静态语句块中的语句合并产生的,编译器收集的顺序由语句在源文件中出现的顺序决定。特别注意的是,静态语句块只能访问到定义在它之前的类变量,定义在它之后的类变量只能赋值,不能访问。例如以下代码:
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
```java ```java
public class Test { public class Test {

View File

@ -1,6 +1,59 @@
<<<<<<< HEAD
# 一、概述 # 一、概述
Redis 是速度非常快的非关系型NoSQL内存键值数据库可以存储键和五种不同类型的值之间的映射。 Redis 是速度非常快的非关系型NoSQL内存键值数据库可以存储键和五种不同类型的值之间的映射。
=======
<!-- GFM-TOC -->
* [一、概述](#一概述)
* [二、数据类型](#二数据类型)
* [STRING](#string)
* [LIST](#list)
* [SET](#set)
* [HASH](#hash)
* [ZSET](#zset)
* [三、数据结构](#三数据结构)
* [字典](#字典)
* [跳跃表](#跳跃表)
* [四、使用场景](#四使用场景)
* [计数器](#计数器)
* [缓存](#缓存)
* [查找表](#查找表)
* [消息队列](#消息队列)
* [会话缓存](#会话缓存)
* [分布式锁实现](#分布式锁实现)
* [其它](#其它)
* [五、Redis 与 Memcached](#五redis-与-memcached)
* [数据类型](#数据类型)
* [数据持久化](#数据持久化)
* [分布式](#分布式)
* [内存管理机制](#内存管理机制)
* [六、键的过期时间](#六键的过期时间)
* [七、数据淘汰策略](#七数据淘汰策略)
* [八、持久化](#八持久化)
* [RDB 持久化](#rdb-持久化)
* [AOF 持久化](#aof-持久化)
* [九、事务](#九事务)
* [十、事件](#十事件)
* [文件事件](#文件事件)
* [时间事件](#时间事件)
* [事件的调度与执行](#事件的调度与执行)
* [十一、复制](#十一复制)
* [连接过程](#连接过程)
* [主从链](#主从链)
* [十二、Sentinel](#十二sentinel)
* [十三、分片](#十三分片)
* [十四、一个简单的论坛系统分析](#十四一个简单的论坛系统分析)
* [文章信息](#文章信息)
* [点赞功能](#点赞功能)
* [对文章进行排序](#对文章进行排序)
* [参考资料](#参考资料)
<!-- GFM-TOC -->
# 一、概述
Redis 是速度非常快的非关系型NoSQL内存键值数据库可以存储键和五种不同类型的值之间的映射。
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
键的类型只能为字符串,值支持五种数据类型:字符串、列表、集合、散列表、有序集合。 键的类型只能为字符串,值支持五种数据类型:字符串、列表、集合、散列表、有序集合。
@ -316,7 +369,11 @@ List 是一个双向链表可以通过 lpop  lpush 写入和读取消
在分布式场景下,无法使用单机环境下的锁来对多个节点上的进程进行同步。 在分布式场景下,无法使用单机环境下的锁来对多个节点上的进程进行同步。
<<<<<<< HEAD
可以使用 Redis 自带的 SETNX 命令实现分布式锁除此之外还可以使用官方提供的 RedLock 分布式锁实现。 可以使用 Redis 自带的 SETNX 命令实现分布式锁除此之外还可以使用官方提供的 RedLock 分布式锁实现。
=======
可以使用 Redis 自带的 SETNX 命令实现分布式锁,除此之外,还可以使用官方提供的 RedLock 分布式锁实现。
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
## 其它 ## 其它
@ -358,7 +415,11 @@ Redis 可以为每个键设置过期时间当键过期时会自动删除
可以设置内存最大使用量,当内存使用量超出时,会施行数据淘汰策略。 可以设置内存最大使用量,当内存使用量超出时,会施行数据淘汰策略。
<<<<<<< HEAD
Redis 具体有 6 种淘汰策略 Redis 具体有 6 种淘汰策略
=======
Redis 具体有 6 种淘汰策略:
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
| 策略 | 描述 | | 策略 | 描述 |
| :--: | :--: | | :--: | :--: |
@ -508,7 +569,11 @@ Sentinel哨兵可以监听集群中的服务器并在主服务器进入
分片是将数据划分为多个部分的方法,可以将数据存储到多台机器里面,这种方法在解决某些问题时可以获得线性级别的性能提升。 分片是将数据划分为多个部分的方法,可以将数据存储到多台机器里面,这种方法在解决某些问题时可以获得线性级别的性能提升。
<<<<<<< HEAD
假设有 4  Redis 实例 R0R1R2R3还有很多表示用户的键 user:1user:2... ,有不同的方式来选择一个指定的键存储在哪个实例中。 假设有 4  Redis 实例 R0R1R2R3还有很多表示用户的键 user:1user:2... ,有不同的方式来选择一个指定的键存储在哪个实例中。
=======
假设有 4 个 Redis 实例 R0R1R2R3还有很多表示用户的键 user:1user:2... ,有不同的方式来选择一个指定的键存储在哪个实例中。
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
- 最简单的方式是范围分片例如用户 id  0~1000 的存储到实例 R0 用户 id  1001~2000 的存储到实例 R1 等等。但是这样需要维护一张映射范围表维护操作代价很高。 - 最简单的方式是范围分片例如用户 id  0~1000 的存储到实例 R0 用户 id  1001~2000 的存储到实例 R1 等等。但是这样需要维护一张映射范围表维护操作代价很高。
- 还有一种方式是哈希分片使用 CRC32 哈希函数将键转换为一个数字再对实例数量求模就能知道应该存储的实例。 - 还有一种方式是哈希分片使用 CRC32 哈希函数将键转换为一个数字再对实例数量求模就能知道应该存储的实例。

View File

@ -1,4 +1,44 @@
<<<<<<< HEAD
# 20. 表示数值的字符串 # 20. 表示数值的字符串
=======
<!-- GFM-TOC -->
* [20. 表示数值的字符串](#20-表示数值的字符串)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [21. 调整数组顺序使奇数位于偶数前面](#21-调整数组顺序使奇数位于偶数前面)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [22. 链表中倒数第 K 个结点](#22-链表中倒数第-k-个结点)
* [解题思路](#解题思路)
* [23. 链表中环的入口结点](#23-链表中环的入口结点)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [24. 反转链表](#24-反转链表)
* [解题思路](#解题思路)
* [递归](#递归)
* [迭代](#迭代)
* [25. 合并两个排序的链表](#25-合并两个排序的链表)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [递归](#递归)
* [迭代](#迭代)
* [26. 树的子结构](#26-树的子结构)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [27. 二叉树的镜像](#27-二叉树的镜像)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [28 对称的二叉树](#28-对称的二叉树)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
* [29. 顺时针打印矩阵](#29-顺时针打印矩阵)
* [题目描述](#题目描述)
* [解题思路](#解题思路)
<!-- GFM-TOC -->
# 20. 表示数值的字符串
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
[NowCoder](https://www.nowcoder.com/practice/6f8c901d091949a5837e24bb82a731f2?tpId=13&tqId=11206&tPage=1&rp=1&ru=/ta/coding-interviews&qru=/ta/coding-interviews/question-ranking) [NowCoder](https://www.nowcoder.com/practice/6f8c901d091949a5837e24bb82a731f2?tpId=13&tqId=11206&tPage=1&rp=1&ru=/ta/coding-interviews&qru=/ta/coding-interviews/question-ranking)

View File

@ -1,4 +1,14 @@
<<<<<<< HEAD
# 一、跨站脚本攻击 # 一、跨站脚本攻击
=======
<!-- GFM-TOC -->
* [一、跨站脚本攻击](#一跨站脚本攻击)
* [二、跨站请求伪造](#二跨站请求伪造)
* [三、SQL 注入攻击](#三sql-注入攻击)
* [四、拒绝服务攻击](#四拒绝服务攻击)
* [参考资料](#参考资料)
<!-- GFM-TOC -->
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
## 概念 ## 概念
@ -34,7 +44,11 @@
### 2. 过滤特殊字符 ### 2. 过滤特殊字符
<<<<<<< HEAD
例如将 `<` 转义为 `&lt;`,将 `>` 转义为 `&gt;`从而避免 HTML  Jascript 代码的运行。 例如将 `<` 转义为 `&lt;`,将 `>` 转义为 `&gt;`从而避免 HTML  Jascript 代码的运行。
=======
例如将 `<` 转义为 `&lt;`,将 `>` 转义为 `&gt;`,从而避免 HTML 和 Javascript 代码的运行。
>>>>>>> 9f680db0cc99bd992c7f979442ecf458a33f9c1b
富文本编辑器允许用户输入 HTML 代码就不能简单地将 `<` 等字符进行过滤了极大地提高了 XSS 攻击的可能性。 富文本编辑器允许用户输入 HTML 代码就不能简单地将 `<` 等字符进行过滤了极大地提高了 XSS 攻击的可能性。