Given:
10. import java.io.*;
11. Class Animal {
12.   Animal(){System.out.print("a");}}
13. Class Dog extends Animal implements Serializable{
14.  Dog(){System.out.print("a");}}
15. public Beagle extends Dog {}If an instance of class Beagle is created, then Serialized,then deSerialized,what is result?
A. ad
B. ada
C. add
D. adad
E. Compilation fails.
F. A exception is thrown at runtime. 选哪个,原因是什么???求解

解决方案 »

  1.   


    14. Dog(){System.out.print("d");}}
    第十四行应该是这样,呵呵,笔误..
      

  2.   

    implements Serializable-相关知识尚未接触,关注
      

  3.   

    可能原因是,首先实例化  出现的是ad没有异议了,然后在序列化的时候,首先序列化A,输出a,然后发现A不是可序列化的类,于是终止了序列化。。后面的就没有输出了。。
      

  4.   

    Java序列化/反序列化  这个确实不了解  顺便帮你顶一下吧
      

  5.   

    更正一下我之前的说法,序列化是不对实例有任何操作的,关键是在反序列化时,需要对反序列化后的Object进行转型,这个时候会对Beagle 进行实例化,在实例化了Animal的时候发现不是可序列化的类,然后就终止了。
      

  6.   

    1.继承是可以继承父类的类和接口的。
    2.创建对象输出ad,序列化:就是把对象以字节形式写入文件,反序列:就是从文件里读出对象,好像之后没用到对象的创建啊,A吧,
      

  7.   

    C
    首先在创建对象的时候输出ad
    序列化的时候不会创建对象,所以不会调用任何构造函数
    在反序列化的时候会重新生成对象,会调用无参数的构造函数,由于Animal类没有实现Serializable接口,所以不会调到Animal的构造函数。
    最终调到Dog的构造函数,输出d
    结果add
      

  8.   

    跑了下程序 确实是ADA 不是AD
      

  9.   

    如果把Animal 也添上implements Serializable 的话 结果就变成AD了
      

  10.   


    写错了,结果是ada!!!import java.io.*;class Animal {
    Animal() {
    System.out.print("a");
    }
    }class Dog extends Animal implements Serializable { private static final long serialVersionUID = 1L; Dog() {
    System.out.print("d");
    }
    }public class Beagle extends Dog { private static final long serialVersionUID = 1L; public static void main(String[] args) {
    Beagle beagle = new Beagle();
    try {
    FileOutputStream fos = new FileOutputStream("test.out");
    ObjectOutputStream oos = new ObjectOutputStream(fos);
    oos.writeObject(beagle);
    oos.close();
    } catch (Exception ex) {
    ex.printStackTrace();
    }
    try {
    FileInputStream fis = new FileInputStream("test.out");
    ObjectInputStream ois = new ObjectInputStream(fis);
    beagle = (Beagle) ois.readObject();
    ois.close();
    } catch (Exception ex) {
    ex.printStackTrace();
    }
    }
    }ois.readObject()说明如下
    The root object is completely restored when all of its fields and the objects it references are completely restored.所以在反序列化时会生成一个root object
      

  11.   

    由于Animal类没有实现Serializable接口,所以不会调到Animal的构造函数。
    这句刚好写反了吧。
    因为Animal没有实现Serializable接口,所以在反系列化的时候,才会调用Animal的无参构造方法来实例化Animail。
    好像前两天刚写了一篇【Java Serializable系列化与反系列化】的文章。
      

  12.   

    结果是ada 反序列化时调用Animal的无参构造函数 所以打印a 但是不知道为什么不调用Dog的构造函数了 构造子类的时候不是应该先调用其所有的父类的构造函数吗?
      

  13.   

    是这样的 它的大概意思是说 构造完了Beagle 的对象之后再进行序列化 反序列化吧 ?  
    我们要明确一点 序列化,比如我们将对象写到磁盘中,其实我们只是将对象的信息 以二进制流的形式写到文件里去,并不涉及到构造函数。
    但是反序列化需要根据对象的信息在内存中重新构造对象,这就涉及到构造函数了 
    基类在实例化的时候 顺序  父类->基类  构造函数是按照这个个顺序执行的
    以上纯属小弟的一点理解  
    我觉得应该是 ad
      

  14.   

    题目比较搞,而且到处是错,如果真要哪天被这么面试搞不定,我直接选E,至少Class首字母大写是编译不了的,我通常都这么干!
    话说回来,这个题目的意图倒是比较有意思,我仔细翻了下Serializable接口的说明,其中有一段非常晦涩难懂(估计是翻译坑爹了,英文不好没办法)的解释说明了这个情况:要允许不可序列化类的子类型序列化,可以假定该子类型负责保存和恢复超类型的公用 (public)、受保护的 (protected) 和(如果可访问)包 (package) 字段的状态。仅在子类型扩展的类有一个可访问的无参数构造方法来初始化该类的状态时,才可以假定子类型有此职责。如果不是这种情况,则声明一个类为可序列化类是错误的。该错误将在运行时检测到。
     在反序列化过程中,将使用该类的公用或受保护的无参数构造方法初始化不可序列化类的字段。可序列化的子类必须能够访问无参数构造方法。可序列化子类的字段将从该流中恢复。题目期望的答案是B:ada(那个d楼主后面说了打错了)。
    真要被这种题目坑到了,就选编译失败,然后跟面试官理论,一上来就指出他们不严谨,语法错误,先占点优势,哈哈,住大家面试好运!
      

  15.   

    我的结果是adpackage com.test;
    import java.io.*;
    class Animal {
    Animal(){System.out.print("a");}
    }
    class Dog extends Animal implements Serializable{
    /**
     * 
     */
    private static final long serialVersionUID = 1L; Dog(){System.out.print("d");}
    }
    public class Beagle extends Dog {





    /**
     * 
     */
    private static final long serialVersionUID = 1L; /**
     * @param args
     */
    public static void main(String[] args) {
    Beagle b = new Beagle(); }


    }

      

  16.   

    JAVA本身的构造器及子父类构造方法的初始化顺序
    当一个对象被创建时,初始化是以下面的顺序完成的: 
    1. 设置成员的值为缺省的初始值 (0, false, null) 
    2. 调用对象的构造方法 (但是还没有执行构造方法体) 
    3. 调用父类的构造方法 
    4. 使用初始化程序和初始块初始化成员 
    5. 执行构造方法体 
    看看在实际中是如何一步一步完成的,看看下面的例子: 
    class A { 
    A() { 
    System.out.println("A.A called"); 


    class B extends A { 
    int i = f(); 
    int j; 

    j = 37; 
    System.out.println("initialization block executed"); 

    B() { 
    System.out.println("B.B called"); 

    int f() { 
    System.out.println("B.f called"); 
    return 47; 


    public class CtorDemo2 { 
    public static void main(String args[]) { 
    B bobj = new B(); 


    程序的输出是: 
    A.A called 
    B.f called 
    initialization block executed 
    B.B called 
    B 的构造方法被调用,但是最先做的事情是隐含的调用父类的构造方法。父类必须自己负责初始化它自己的状态而不是让子类来做。 然后B对象的成员被初始化,这包含一个对B.f 的调用和包围在{}中的初始块的执行。最后B的构造方法体被执行。 
      

  17.   

    是ada 程序在执行时候是先实现继承再实现接口的。
      

  18.   

    说真的,如果只有笔试的话,你选E他照样给你算错,因为他根本不认为他的Class写的有问题,也许是他自己的笔误,你连和他理论的机会都没有,就被pass了