(1)普通代码块:就是类中方法的方法体
public void xxx(){
//code
}
(2)构造块:用{}裹起来的代码片段,构造块在创建对象时会被调用,每次创建对象
时都会被调用,并且优先于类构造函数执行。
{
//code
}
(3)静态块:用static{}裹起来的代码片段,只会被执行一次(第一次加载此类时执行,比如说用Class.forName("")加载类时就会执行 static block),静态块优先于构造块执行。如果某些代码必须要在项目启动时候就执行的时候,我们可以采用静态代码块,这种代码是主动执行的。静态代码块可以用来初始化一些项目最常用的变量和对象。
static{
//code
}
(4)同步代码块:使用synchronized(obj){}裹起来的代码块,在多线程环境下,对共享数据进行读写操作是需要互斥进行的,否则会导致数据的不一致性。常见的是synchronized用来修饰方法,其语义是任何线程进入synchronized需要先取得对象锁如果被占用了,则阻塞,实现了互斥访问共享资源。而synchronized也是有代价的。
一个常见的场景是,一个冗长的方法中,其实只有一小段代码需要访问共享资源,这时使用同步块,就只将这小段代码裹在synchronized block,既能够实现同步访问,也能够减少同步引入的开销。
synchronized(obj){
//code
}
执行顺序:静态代码块>静态函数(不调用时不显示,先加载进来)>主函数>构造代码块>构造函数>普通代码块对于继承关系而言。先执行构造链上的所有静态代码块,再依次按照非静态代码块的顺序,执行继承链上非静态代码块。
对于类体内部生成对象的情况,静态代码块第一次加载时执行,即仅仅会在最外侧执行。
public class test
{
public static test t1 = new test();
public static test t2 = new test();
public test(){
System.out.println("构造块1");
}
{
System.out.println("构造块2");
}
static
{
System.out.println("静态块");
}
public static void main(String[] args)
{
test t = new test();
}
}输出如:
构造块2
构造块1
构造块2
构造块1
静态块
构造块2
构造块1
false
3.向上转型和向下转型
向上转型:子类对象给父类引用,类型提升,动物x=new猫;
向下转型:父类的引用指向自己子类类型,强制转换;动物x=new 猫 ,猫y=(猫)x
但是不能将父类的对象转换成子类类型,动物x=new 动物 猫 y=(猫)x
多态自始至终都是子类对象在做改变。