💟这里是CS大白话专场,让枯燥的学习变得有趣!
💟没有对象不要怕,我们new一个出来,每天对ta说不尽情话!
💟好记性不如烂键盘,自己总结不如收藏别人!
static
💌 static 表示静态,可以修饰成员方法(静态方法)、成员变量(静态变量)。
静态变量
🍠 特点:被该类所有对象共享。
🍠 调用方式:类名调用、对象名调用。
P.S. 当用类名调用的时候,静态变量是优先于对象存在的,随着类的加载而加载到堆内存的静态存储区。
静态方法
🍠 特点:多用在测试类和工具类中。
🍠 调用方式:类名调用、对象名调用。
P.S. 静态方法只能访问静态变量和静态方法,没有 this 关键字。
final
💌 final 修饰方法为最终方法,不能被重写;修饰类为最终类,不能被继承;修饰变量为常量,只能被赋值一次,若变量为基本类型则数值不能改变,若变量为引用类型则地址值不能改变,内部属性可以改变。
volatile
💌 volatile 主要作用:实现并发编程下共享变量的可见性,禁止指令重排,不能保证原子性操作,也不能保证多线程安全。
重排序:为了提高性能,编译器和处理器常常会对既定的代码执行顺序进行指令重排序。原因:一个好的内存模型实际上会放松对处理器和编译器规则的束缚,也就是说软件技术和硬件技术都为同一个目标而进行奋斗:在不改变程序执行结果的前提下,尽可能提高执行效率。JMM 对底层尽量减少约束,使其能够发挥自身优势。因此,在执行程序时,为了提高性能,编译器和处理器常常会对指令进行重排序。一般重排序可以分为如下三种:
🍠 编译器优化的重排序:编译器在不改变单线程程序语义的前提下,重新安排语句的执行顺序;
🍠 指令级并行的重排序:现代处理器采用了指令级并行技术来将多条指令重叠执行。如果不存在数据依赖性,处理器可以改变语句对应机器指令的执行顺序;
🍠 内存系统的重排序:由于处理器使用缓存和读/写缓冲区,这使得加载和存储操作看上去可能是在乱序执行的。
变量被 volatile 修饰后,编译器会保证每次访问该变量时都从内存中读取最新值,并且将该变量的修改立即写入到内存中。这样可以保证多个线程同时访问该变量时能够看到正确的值。