JavaSE继承与多态练习题

练习一

有父类Base,内部定义了x、y属性。有子类Sub,继承自父类Base。子类新增了一个z属性,并且定义了calculate方法,在此方法内计算了父类和子类中x、y、z属性三者的乘积。请补全子类构造方法的初始化逻辑,使得该计算逻辑能够正确执行。

输入描述:

三个整数:x, y, z

输出描述:

三个整数的乘积:x*y*z

本题主要考察在继承关系上,构造方法的使用。

  1. 当子类继承父类之后,要先帮助父类进行成员的初始化,此时需要通过super关键字来实现。
  2. 同时初始化子类自己的成员。

 

import java.util.Scanner;

public class Main {

    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        while (scanner.hasNextInt()) {
            int x = scanner.nextInt();
            int y = scanner.nextInt();
            int z = scanner.nextInt();
            Sub sub = new Sub(x, y, z);
            System.out.println(sub.calculate());
        }
    }

}

class Base {

    private int x;
    private int y;

    public Base(int x, int y) {
        this.x = x;
        this.y = y;
    }

    public int getX() {
        return x;
    }

    public int getY() {
        return y;
    }

}

class Sub extends Base {

    private int z;

    public Sub(int x, int y, int z) {

        //write your code here
        super(x,y);
        this.z = z;
    }

    public int getZ() {
        return z;
    }

    public int calculate() {
        return super.getX() * super.getY() * this.getZ();
    }

}

练习二

A 派生出子类 B , B 派生出子类 C ,并且在 java 源代码有如下声明:

1. A a0=new A();

2. A a1=new B();

3. A a2=new C();

问以下哪个说法是正确的?()

A.只有第一行能通过编译

B.第1、2行能通过编译,但第3行编译出错

C.第1、2、3行能通过编译,但第2、3行运行时出错

D.第1行,第2行和第3行的声明都是正确的

本题描述的代码如下:

class A {

}
class B extends A {

}
class C extends B {

}
public class Test {

    public static void main(String[] args) {
        A a0=new A();//1

        A a1=new B();//2

        A a2=new C();//3
    }
}

主要疑问就是注释3处,此时A虽然不是C的直接父类,但是C依然间接继承了A的内容的,此时可以发生向上转型的。

练习三

以下代码运行结果

class Base {
  Base() {
  	System.out.print("Base"); 
  }
}

public class Alpha extends Base {
 
  public static void main( String[] args ) {
    new Alpha();//1
    //调用父类无参的构造方法
    new Base();//2
  } 
}

 

A.Base

B.BaseBase

C.编译失败

D.代码运行但没有输出

E.运行时抛出异常

 

继承关系上的执行顺序。

当子类继承父类之后,在实例化子类对象的时候,先要调用父类的构造方法,来帮助父类初始化。上述代码相当于如下代码:

class Base {
  Base() {
  	System.out.print("Base"); 
  }
}

public class Alpha extends Base {
  Alpha() {
     super();
  }
  public static void main( String[] args ) {
    new Alpha();//1
    //调用父类无参的构造方法
    new Base();//2
  } 
}

编译器会默认提供如上的子类的构造方法。

所以,注释1处输出的结果为Base,注释2处输出的结果为:Base

最终结果是BaseBase。故:选择B;

练习四

以下程序的输出结果

 

class Base{
  public Base(String s){
    System.out.print("B");
  }
}

public class Derived extends Base{
  public Derived (String s) {
    System.out.print("D");
  }
  public static void main(String[] args){
    new Derived("C");
  }
}

A.BD

B.DB

C.C

D.编译错误

当子类继承父类需要先初始化继承过来的父类的成员,此时需要通过super来完成。很明显在子类的构造方法当中,并没有通过super调用父类的构造方法。正确写法应该是:

class Base{
  public Base(String s){
    System.out.print("B");
  }
}

public class Derived extends Base{
  public Derived (String s) {
    super(s);
    System.out.print("D");
  }
  public static void main(String[] args){
    new Derived("C");
  }
}

练习五

class X{
	Y y=new Y();//1
	public X(){//2
		System.out.print("X");
	}
}
class Y{
	public Y(){//3
		System.out.print("Y");
	}
}
public class Z extends X{
	Y y=new Y();//4
	public Z(){//5
		System.out.print("Z");
	}
	public static void main(String[] args) {
		new Z();
	}
}

本题考察代码的执行顺序:

类Z继承类X。

在继承层次上,先执行父类和子类的静态的,再执行父类的实例,父类的构造,最后执行子类的实例和子类的构造。

根据以上顺序,我们得出结论:本题中没有静态的。所以先执行1和2,再执行4和5。执行注释1和注释4的时候,分班打印Y。故最终的结果是YXYZ。

练习六

以下关于关键字super的描述中,正确的是:

A.super关键字只代表当前对象内部的那一块父类型特征,不包含在子类对象中

B.super关键字不仅可以指代子类的直接父类,还可以直接指代父类的父类

C.子类通过super关键字只能调用父类的方法,而不能调用父类的属性

D.子类通过super关键字只能调用父类的属性,而不能调用父类的方法

本题中主要考察关键字super。首先3种用法为:

1.super.data访问父类中的属性

2.super.func() 访问父类的方法

3.super() 访问父类的构造方法

根据这3点,选项C和D均错。

B中:super只能指代其直接父类,不能指代父类的父类

A正确,super关键字只是在代码层次上提高了代码的阅读性。在子类中代表继承过来的父类型的特征。通过super.data就能知道访问的是父类的data。

 练习七

以下代码输出结果

public class Person{

	private String name = "Person";

	int age=0;

}

public class Child extends Person{

	public String grade;

	public static void main(String[] args){

		Person p = new Child();

		System.out.println(p.name);

	}

}

本题主要考察继承和访问修饰限定符private

子类继承父类之后,会继承父类私有的数据,但是由于private访问修饰符的问题,子类没有办法直接反问该数据。

练习八

在 java 中,一个类可同时定义为许多同名的方法,这些方法的形式参数个数,类型或顺序各不相同,传回的值可能各不相同,这种面向对象的特性称为(c)

A.隐藏

B.重写

C.重载

D.无此特性

练习九

以下说法, 描述错误的是:B

A.重载要求两个方法名字相同, 但是参数的类型和个数不同, 不要求返回值类型相同

B.重写要求两个方法名字相同, 同时参数的类型和个数相同, 不要求返回值类型相同

C.重写的方法可以使用 @Override 注解来修饰

D.父类的方法为 private 的时候, 子类方法不能进行重写.

 练习十

以下代码输出    BD

class B {
    public int Func() {
        System.out.print("B");
        return 0;
    }
}
class D extends B {
    @Override
    public int Func() {
        System.out.print("D");
        return 0;
    }
}
public class Test {
    public static void main(String[] args) {
        B a = new B();
        B b = new D();
        a.Func();
        b.Func();
    }
}

 

  • 17
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值