java上溯造型_think-in-java/6.7 上溯造型.md at master · quanke/think-in-java · GitHub

6.7 上溯造型

继承最值得注意的地方就是它没有为新类提供方法。继承是对新类和基础类之间的关系的一种表达。可这样总结该关系:“新类属于现有类的一种类型”。

这种表达并不仅仅是对继承的一种形象化解释,继承是直接由语言提供支持的。作为一个例子,大家可考虑一个名为Instrument的基础类,它用于表示乐器;另一个衍生类叫作Wind。由于继承意味着基础类的所有方法亦可在衍生出来的类中使用,所以我们发给基础类的任何消息亦可发给衍生类。若Instrument类有一个play()方法,则Wind设备也会有这个方法。这意味着我们能肯定地认为一个Wind对象也是Instrument的一种类型。下面这个例子揭示出编译器如何提供对这一概念的支持:

//: Wind.java

// Inheritance & upcasting

import java.util.*;

class Instrument {

public void play() {}

static void tune(Instrument i) {

// ...

i.play();

}

}

// Wind objects are instruments

// because they have the same interface:

class Wind extends Instrument {

public static void main(String[] args) {

Wind flute = new Wind();

Instrument.tune(flute); // Upcasting

}

} ///:~

这个例子中最有趣的无疑是tune()方法,它能接受一个Instrument句柄。但在Wind.main()中,tune()方法是通过为其赋予一个Wind句柄来调用的。由于Java对类型检查特别严格,所以大家可能会感到很奇怪,为什么接收一种类型的方法也能接收另一种类型呢?但是,我们一定要认识到一个Wind对象也是一个Instrument对象。而且对于不在Wind中的一个Instrument(乐器),没有方法可以由tune()调用。在tune()中,代码适用于Instrument以及从Instrument衍生出来的任何东西。在这里,我们将从一个Wind句柄转换成一个Instrument句柄的行为叫作“上溯造型”。

6.7.1 何谓“上溯造型”?

之所以叫作这个名字,除了有一定的历史原因外,也是由于在传统意义上,类继承图的画法是根位于最顶部,再逐渐向下扩展(当然,可根据自己的习惯用任何方法描绘这种图)。因素,Wind.java的继承图就象下面这个样子:

由于造型的方向是从衍生类到基础类,箭头朝上,所以通常把它叫作“上溯造型”,即Upcasting。上溯造型肯定是安全的,因为我们是从一个更特殊的类型到一个更常规的类型。换言之,衍生类是基础类的一个超集。它可以包含比基础类更多的方法,但它至少包含了基础类的方法。进行上溯造型的时候,类接口可能出现的唯一一个问题是它可能丢失方法,而不是赢得这些方法。这便是在没有任何明确的造型或者其他特殊标注的情况下,编译器为什么允许上溯造型的原因所在。

也可以执行下溯造型,但这时会面临第11章要详细讲述的一种困境。

再论合成与继承

在面向对象的程序设计中,创建和使用代码最可能采取的一种做法是:将数据和方法统一封装到一个类里,并且使用那个类的对象。有些时候,需通过“合成”技术用现成的类来构造新类。而继承是最少见的一种做法。因此,尽管继承在学习OOP的过程中得到了大量的强调,但并不意味着应该尽可能地到处使用它。相反,使用它时要特别慎重。只有在清楚知道继承在所有方法中最有效的前提下,才可考虑它。为判断自己到底应该选用合成还是继承,一个最简单的办法就是考虑是否需要从新类上溯造型回基础类。若必须上溯,就需要继承。但如果不需要上溯造型,就应提醒自己防止继承的滥用。在下一章里(多形性),会向大家介绍必须进行上溯造型的一种场合。但只要记住经常问自己“我真的需要上溯造型吗”,对于合成还是继承的选择就不应该是个太大的问题。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/527021.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

java 官网下载jdk源码_openJDK之如何下载各个版本的openJDK源码

如果我们需要阅读openJDK的源码,那么需要下载,那么该去哪下载呢?现在JDK已经发展到版本10了,11已经处于计划中,如果需要特定版本的openJDK,它们的下载链接在哪呢?1.openJDK的项目图1 可以看到有openJDK6、openJDK7、…

java 这么获取农历_用JAVA查询中国农历年

用来查询农历年的代码,可能比较粗糙,希望不要太打击偶,哈哈。一,Console.java[用来获取控制台的输入]/*#()Console.java 20:40:25 2/2/2006控制台消息输入/输出。*/import java.io.*;import java.text.SimpleDateFormat;import ja…

java 最大分词算法_Java实现的最大匹配分词算法详解

本文实例讲述了java实现的最大匹配分词算法。分享给大家供大家参考,具体如下:全文检索有两个重要的过程:1分词2倒排索引我们先看分词算法目前对中文分词有两个方向,其中一个是利用概率的思想对文章分词。 也就是如果两个字&#x…

java 集合迭代器_Java中的集合迭代器

集合的迭代器任何集合都有迭代器。任何集合类,都必须能以某种方式存取元素,否则这个集合容器就没有任何意义。迭代器,也是一种模式(也叫迭代器模式)。在java中它是一个对象,其目的是遍历并选中其中的每个元素,而使用者…

git关闭密码自动存储_项目在 git 里怎样合理的保存配置文件(服务器密码等敏感内容)...

办法其实很多,有两种较常用。第一种是配置文件不提交真实内容,只提交一个模板文件。每个开发者克隆之后按照自己的环境补完配置文件,这样自然而然就独立出来了(需更改文件名并忽略有效配置文件)。如果配置文件很大配置项很多,此法…

isfull mysql_Mysql8.0及以上版本,关于only_full_group_by的问题

mysql8.0及以上版本,关于only_full_group_by的问题:ERROR 1055 (42000): Expression #7 of SELECT list is not in GROUP BY clause and contains nonaggregated column postscan.verifyDelayLog.auditor which is not functionally dependent on column…

java jnotify_Jnotify文件监控的用法以及Jar文件导入的方法

简介Jnotiy, 支持动态监控(支持级联监控)文件夹和文件的jar包。在linux中,调用linux底层的jnotify服务。在windows中,需要添加附件的dll文件。因为通用的Maven仓库中没有此Jar文件,pom.xml文件需要如下配置:net.contentobjects.jn…

java 异常练习题_Java 异常(习题)

异常Key Point* 异常的概念和分类* 异常的产生和传递* 异常的处理* 自定义异常练习1. 填空Java 中所有的错误都继承自throwable类;在该类的子类中,Error类表示严重的底层错误,对于这类错误一般处理的方式是不要求我们对其处理Exception类表示…

mysql 半同步 主主_MySQL主从,半同步,主主复制

MySQL Replication我们知道,MySQL数据库的二进制日志记录着每一个明确或者潜在可能导致数据库发生改变的sql语句,因此我们可以基于二进制日志来实现mysql的主从一致。而我们在此提到的mysql的复制的简单过程就是:首先mysql的主服务器(Master)…

java local_java.time.LocalDateTime with()方法

java.time.LocalDateTime with()方法java.time.LocalDateTime.with(TemporalAdjuster adjuster)方法返回此日期时间的调整副本。1 语法public LocalDateTime with(TemporalAdjuster adjuster)2 参数adjuster:要使用的调整器,而不是null。3 返回值一个Loc…

java 数据队列_Java 数据结构 - 队列

Java 数据结构 - 队列我们今天要讲的数据结构是队列,比如 Java 线程池任务就是队列实现的。1. 什么是队列和栈一样,队列也是一种操作受限的线性结构。使用队列时,在一端插入元素,而在另一端删除元素。1.1 队列的主要特性队列中的数…

java中死锁_关于java中死锁的总结

关于死锁,估计很多程序员都碰到过,并且有时候这种情况出现之后的问题也不是非常好排查,下面整理的就是自己对死锁的认识,以及通过一个简单的例子来来接死锁的发生,自己是做python开发的,但是对于死锁的理解…

eclipse java的jvm匹配_eclipse设置jvm

Java虚拟机默认分配64M内存,如果你的应用比较大,超出64M内存,Java虚拟机就会抛出outOfMemoryError,并停止运行。不管是什么应用(Web应用、Application等),只需要修改你的机器上的运行Java命令,在javaxxx命令…

java+set+split_阿里资深工程师教你如何优化 Java 代码!

原标题:阿里资深工程师教你如何优化 Java 代码!作者 | 王超责编 | 伍杏玲明代王阳明先生在《传习录》谈为学之道时说:私欲日生,如地上尘,一日不扫,便又有一层。着实用功,便见道无终穷&#xff0…

java返回特定下标元素_java基础--输出数组中指定元素的下标

java基础--输出数组中指定元素的下标java基础--输出数组中指定元素的下标package com.lcn.day05;public class ArrayDemo8 {/*** 输出数组指定元素的下标*/public static void main(String[] args) {//定义一个数组int[] array new int[]{123,456,789,321,654,987};int index …

java钱币换算_Java编写钱币转换为大写程序

import java.text.DecimalFormat;public class ChangeMonney {private static final String[] STR_UNIT {"零", "壹", "贰", "叁", "肆", "伍","陆", "柒", "捌", "玖"…

java mongodb 使用场景_mongodb使用场景一般是什么?mongodb有哪些基本命令?

此前我们已经充分了解过了mongodb的原理及各种概念,你们知道一般在什么场景下才会使用mongodb吗?下面通过文章来了解一下吧。一、mongodb基本命令1)、数据库切换use admin;2)、浏览当前数据库db;3)、浏览全部数据库show dbs;4)、删除数据库use test;db.dropDatabas…

java desktop mailto,mailto在Java?

I am trying to set a hyperlink in my eclipse java project.when someone clicks on a button, it should open up an email client along with the givenemail id. is it possible to implement it with java.awt.Desktop?解决方案Yes it is possible using desktop.mail()…

myVariable是java标识符吗_java 标识符与变量

一、Java 标识符三要素1.标识符由字母、下划线(_)、美元符号($)或者字母组成。2.标识符应以字母、下划线(_)、美元符开头。3.标识符字符大小写敏感,长度无限制。标识符最重要的就是 见名知意并且不能与java关键字重名!二、Java 变量1.java变量是程序中最基本的单元。…

使java代码更干净_java如何使用Lombok更优雅地编码

Lombok简介和其他语言相比,Java经常因为不必要的冗长被批评。Lombok提供了一系列注解用以在后台生成模板代码,将其从你的类中删除,从而有助于保持你的代码整洁。较少的模板意味着更简洁的代码,更易于阅读和维护。在本文中&#xf…