A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 张超超 黑马帝   /  2012-4-16 14:13  /  3057 人查看  /  8 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

class StaticSuper{
    static{
        System.out.println("super static block");
    }
    StaticSuper(){
        System.out.println("super constructor");
    }
}
public class StaticTests extends StaticSuper{
    static int rand;
    static{
        rand=(int)(Math.random()*6);
        System.out.println("static block "+rand);
    }
    StaticTests(){
        System.out.println("constructor");
    }
    public static void main(String[] args){
        System.out.println("in main");
        StaticTests st=new StaticTests();
    }
}

为什么运行结果第一行输出的是
super static block
而不是
static block

评分

参与人数 1技术分 +1 收起 理由
贠(yun)靖 + 1

查看全部评分

8 个回复

倒序浏览
加载一个类时,它的静态初始化代码被执行。静态初始化代码段与静态变量的初始化同时进行,它们按词法顺序执行。
为什么先加载父类,可以这么理解,没有父亲就生不出儿子{:soso_e112:}。
我觉得更应该思考加注意的是静态初始化代码比main先执行。

评分

参与人数 1技术分 +1 收起 理由
贠(yun)靖 + 1

查看全部评分

回复 使用道具 举报
static{
       super();//这里默认隐式的super()语句;所以第一句一定是super static block
        rand=(int)(Math.random()*6);
        System.out.println("static block "+rand);
    }

在对子类对象进行初始化时,父类的构造函数也会运行,
那是因为子类的构造函数默认第一行有一条隐式的语句 super();
super():会访问父类中空参数的构造函数。而且子类中所有的构造函数默认第一行都是super();

为什么子类一定要访问父类中的构造函数?
因为父类中的数据子类可以直接获取。所以子类对象在建立时,需要先查看父类是如何对这些数据进行初始化的。
所以子类在对象初始化时,要先访问一下父类中的构造函数。
如果要访问父类中指定的构造函数,可以通过手动定义super语句的方式来指定。

评分

参与人数 1技术分 +1 收起 理由
贠(yun)靖 + 1 你是不是也开始要技术分了?审核都过了吧?.

查看全部评分

回复 使用道具 举报
因为父类中有一个静态代码块,在父类进入内存时就可以直接执行,不用调用,当然也不会被复写(复写的是成员变量和成员函数,代码块不是两者之一不能被复写)
回复 使用道具 举报
原来如此,子类静态代码块也隐含父类了。学习了
回复 使用道具 举报
类的初始化过程
初始化一个类须先初始化成员属性
初始化一个子类须先初始化父类
所以先执行父类的成员属性快中的打印语句
回复 使用道具 举报
本帖最后由 如梦初醒 于 2012-4-16 19:52 编辑

为什么运行结果第一行输出的是
super static block
而不是
static block


我的回答所有的Java虚拟机实现必须在每个类或接口被Java程序“首次主动使用”时才初始化他们,初始化一个类就是为类的静态变量赋初值,静态变量的初始化有两种途径:1.在静态变量申明处;2.静态代码块中。
类的首次主动首次主动使用分六种情况:
1.Class.forName("")这个类;
2.初始化化一个类的子类;
3.访问某个类或接口的静态变量,或者对该静态变量赋值;
4.调用类的静态方法
5.调用类的构造方法(也就是new出一个对象);
6.启动类(如:包含main方法的那个类);
基于以上分析, StaticTests含有main方法为启动类,JVM认为这是对 StaticTests类的首次主动使用,
会对其进行初始化化,但这个类继承于StaticSuper类,那么JVM将首先初始化StaticSuper这个类,
初始化StaticSuper这个类就会执行初始化语句 static{
        System.out.println("super static block");
    }
回复 使用道具 举报
邓斌 中级黑马 2012-4-16 20:20:02
8#
可以看看。
http://bbs.itheima.com/forum.php?mod=viewthread&tid=11637
此贴楼主代码很有验证性。。本人回复也不错。。呵呵。
回复 使用道具 举报
蒋亮 中级黑马 2012-4-16 22:16:52
9#
子类继承父类,重用父类的方法、属性,也就是说父类有的子类都有,先继承父类的再扩展自己的,而静态代码块是按静态代码块的顺序执行的,所以第一行打印出来的是super static block
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马