从之前的文章中分享过的一些知识,从Box派生的类并没有体现出它们的实际上是多么有效和强大。例如,BoxWeight构造函数明确的初始化了Box( )的width、height和depth成员。

这些重复的代码在它的超类中已经存在,这样做效率很低,而且,这意味着子类必须被同意具有访问这些成员的权力。然而,有时你希望创建一个超类,该超类可以保持它自己实现的细节(也就是说,它保持私有的数据成员)。这种情况下,子类没有办法直接访问或初始化它自己的这些变量。既然封装是面向对象的基本属性,Java提供了该问题的解决方案是不值得奇怪的。

任何时候一个子类需要引用它直接的超类,它可以用关键字super来实现。super有两种通用形式。第一种调用超类的构造函数。第二种用来访问被子类的成员隐藏的超类成员。下面分别介绍每一种用法(第二种下个文章中介绍)。

使用super调用超类构造函数
子类可以调用超类中定义的构造函数方法,用super的下面形式:

super(parameter-list);

这里,parameter-list定义了超类中构造函数所用到的所有参数。super( )必须是在子类构造函数中的第一个执行语句。为了了解怎样运用super( ),考虑下面BoxWeight( )的改进版本:

// BoxWeight now uses super to initialize its Box attributes.
class BoxWeight extends Box { double weight; // weight of box // initialize width, height, and depth using super() BoxWeight(double w, double h, double d, double m) { super(w, h, d); // call superclass constructor weight = m; }
}

这里,BoxWeight( )调用带w、h和d参数的super( )方法。这使Box( )构造函数被调用,用w、h和d来初始化width, height, 和 depth。BoxWeight不再自己初始化这些值。它只需初始化它自己的特殊值:weight。这种方法使Box可以自由的根据需要把这些值声明成private。

上面的例子,调用super( )用了三个参数。既然构造函数可以被重载,可以用超类定义的任何形式调用super( ),执行的构造函数将是与所传参数相匹配的那一个。

例如,下面是BoxWeight一个完整的实现,BoxWeight具有以不同方法构造盒子的构造函数。在每种情况下,用适当的参数调用super( )。注意width, height, and depth在Box是私有的。

// A complete implementation of BoxWeight.
class Box { private double width; private double height; private double depth; // construct clone of an object Box(Box ob) { // pass object to constructor width = ob.width; height = ob.height; depth = ob.depth; } // constructor used when all dimensions specified Box(double w, double h, double d) { width = w; height = h; depth = d; } // constructor used when no dimensions specified Box() { width = -1; // use -1 to indicate height = -1; // an uninitialized depth = -1; // box } // constructor used when cube is created Box(double len) { width = height = depth = len; } // compute and return volume double volume() { return width * height * depth; }
}
// BoxWeight now fully implements all constructors.
class BoxWeight extends Box { double weight; // weight of box // construct clone of an object BoxWeight(BoxWeight ob) { // pass object to constructor super(ob); weight = ob.weight; } // constructor when all parameters are specified BoxWeight(double w, double h, double d, double m) { super(w, h, d); // call superclass constructor weight = m; } // default constructor BoxWeight() { super(); weight = -1; } // constructor used when cube is created BoxWeight(double len, double m) { super(len); weight = m; }
}
class DemoSuper { public static void main(String args[]) { BoxWeight mybox1 = new BoxWeight(10, 20, 15, 34.3); BoxWeight mybox2 = new BoxWeight(2, 3, 4, 0.076); BoxWeight mybox3 = new BoxWeight(); // default BoxWeight mycube = new BoxWeight(3, 2); BoxWeight myclone = new BoxWeight(mybox1); double vol; vol = mybox1.volume(); System.out.println("Volume of mybox1 is " + vol); System.out.println("Weight of mybox1 is " + mybox1.weight); System.out.println(); vol = mybox2.volume(); System.out.println("Volume of mybox2 is " + vol); System.out.println("Weight of mybox2 is " + mybox2.weight); System.out.println(); vol = mybox3.volume(); System.out.println("Volume of mybox3 is " + vol); System.out.println("Weight of mybox3 is " + mybox3.weight); System.out.println(); vol = myclone.volume(); System.out.println("Volume of myclone is " + vol); System.out.println("Weight of myclone is " + myclone.weight); System.out.println(); vol = mycube.volume(); System.out.println("Volume of mycube is " + vol); System.out.println("Weight of mycube is " + mycube.weight); System.out.println(); }
}

该程序产生下面的输出:

Volume of mybox1 is 3000.0
Weight of mybox1 is 34.3
Volume of mybox2 is 24.0
Weight of mybox2 is 0.076
Volume of mybox3 is -1.0
Weight of mybox3 is -1.0
Volume of myclone is 3000.0
Weight of myclone is 34.3
Volume of mycube is 27.0
Weight of mycube is 2.0

特别注意BoxWeight( )中的这个构造函数:

// construct clone of an object
BoxWeight(BoxWeight ob) { // pass object to constructor super(ob); weight = ob.weight;
}

注意super( )被用一个BoxWeight类型而不是Box类型的对象调用。这仍然调用了构造函数Box(Box ob)。前面已经提醒过,一个超类变量可以引用作为任何一个从它派生的对象。

因此,我们可以传递一个BoxWeight对象给Box构造函数。当然,Box只知道它自己成员的信息。

让我们复习super( )中的关键概念。当一个子类调用super( ),它调用它的直接超类的构造函数。这样,super( )总是引用调用类直接的超类。这甚至在多层次结构中也是成立的。

还有,super( )必须是子类构造函数中的第一个执行语句。

什么是super?如何使用super调用超类构造函数?相关推荐

  1. java 实例方法直接调用超类的实例方法_类方法和实例方法的调用 super this 访问控制符...

    一.类方法和实例方法的调用 先看一道选择题: 下列哪种说法是正确的( ) A. 实例方法可直接调用超类的实例方法 B. 实例方法可直接调用超类的类方法 C. 实例方法可直接调用其他类的实例方法 D. ...

  2. 【Kotlin】Kotlin 类的继承 三 ( super 关键字使用 | super@ 外部调用父类方法 | 子类选择性调用 父类 / 接口 方法 super )

    文章目录 I . 子类调用父类总结 II . 子类调用父类方法 ( super ) III . 子类内部类调用父类方法 ( super@ ) IV . 子类选择调用不同的 父类 / 接口方法 ( su ...

  3. java super.start,java – 在字节码中确定哪里是super()方法调用所有构造函数必须在JVM上执行...

    实际上,字节码构造函数的规则比Java的规则要宽松得多. 唯一的规则是必须在任何正常返回的路径上调用一个构造函数,如果构造函数调用抛出异常,那么您也必须抛出异常. 除此之外,这意味着构造函数可能包含对 ...

  4. java super父类方法_java super关键字,super调用父类构造方法详解

    因为子类不可以继承父类的构造方法,所以,想要调用父类的构造方法的话,那么就可以使用得到super关键字下面的话就来对这个方面做一下详细的讲解. super关键字能够用来访问父类的构造方法.普通方法和属 ...

  5. Java super关键字:super调用父类的构造方法、利用super访问父类成员

    由于子类不能继承父类的构造方法,因此,要调用父类的构造方法,必须在子类的构造方法体的第一行使用 super() 方法.该方法会调用父类相应的构造方法来完成子类对象的初始化工作. 在以下情况下需要使用 ...

  6. java super()方法_Java super关键字的使用方法详解

    构造方法中的super关键字 在Java子类的构造方法中可以通过super关键字来调用父类的构造方法.其用法为: 1) super(); 访问父类中的无参构造函数 2) super (paras-); ...

  7. Java中super关键字及super()的使用

    Java中super关键字及super()的使用: 1.super的使用: (1)super是一个关键字. (2)super和this很类似,我们对比着学习. 2.先复习一下this关键字的使用. ( ...

  8. RTX3060Ti和RTX2060 SUPER,RTX2080 SUPER、RTX3070显卡参数参数对比哪个好 差距大不大

    NVIDIA Ampere架构拥有全新的RT Core(光线追踪核心).Tensor Core(张量核心)和SM(流式多处理器). 选RTX3060Ti和RTX2060 SUPER,RTX2080 S ...

  9. java 调用其他构造函数_我如何在Java中调用另一个构造函数?

    是的,这是可能的: public class Foo { private int x; public Foo() { this(1); } public Foo(int x) { this.x = x ...

最新文章

  1. PowerPoint动画制作时的需要注意的N个事项
  2. SqlServer SqlBulkCopy批量插入 -- 多张表同时插入(事务)
  3. C#委托、事件学习之(三)——热水器烧水案例
  4. linux 从一台服务器向另台服务器复制文件
  5. 【Android】ArcFaceDemo
  6. 【VS2010学习笔记】【异常处理】一(无法启动此程序,因为计算机中丢失libiconv-2.dll)
  7. IF YOU HAVE A NEW LICENSE, PLEASE UPDATE IT
  8. WinForm中的特殊窗体效果:渐变窗口和信息提示窗口
  9. A[1062]德才论 好题
  10. IDEA的xml注释的顶格和空格问题
  11. c语言 pow函数及pow函数的错误情况
  12. c语言判断一个数是否为素数思路,C语言判断一个数是否为素数方法解析
  13. origin数据平滑_科学网-关于origin曲线平滑处理 lowess-叶小球的博文
  14. 长连接、短连接和心跳(有图有案例)
  15. 偏微分方程matlab课件,MATLAB偏微分方程求解.ppt
  16. 猫哥教你写爬虫 041--模拟登录-cookie
  17. 小目标 | 4周学会用邮箱管理时间和工作流
  18. 老广人为粤语---广州话写篇文章
  19. 天长地久 (20分)
  20. 区块链广告平台--【AdRealm】

热门文章

  1. [转载] python之numpy的基本使用
  2. 怎样从外网访问自己的HTTP服务器
  3. iOS 中delegate的理解与使用(传值)
  4. BZOJ-1507 文本编辑器(Editor)
  5. thinkphp 前台html调用函数 格式化输出
  6. 从程序员到项目经理(24):慎于问敏于行 - 忠于工作不等于奴性
  7. Linux中的sh+source+export
  8. 数据结构上机实践第四周项目2 - 建设“单链表”算法库
  9. linux文件内核目录,Linux内核目录文件简介
  10. 编写一个java程序_鼠标在java窗口上的坐标_请问如何在Java中获取窗口外部的鼠标单击坐标...