[读书笔记]Core Java: Volume I - Fundamentals Chapter 5

Title: Core Java — Volume I Fundamentals
Edition: Eleventh Edition
Author: Cay S. Horstmann
读书笔记:对原书的归纳、总结、补充和疑问。

Chapter 5 Inheritance

Inheritance 是面向对象编程最重要的特点之一。
前言大概解释了一下 Inheritance 是什么,然后略微说了一下 reflection 是什么,并且告知读者,reflection 比较难,没必要在意。

光看目录的话,我是不太明白这一章的结构安排的,有提到 Array List,Object Wrappers,Enumeration,Reflection 等等。 不会觉得杂乱无章吗?除非这些各种各样的概念都是和 Inheritance 有关的,要么是利用 inheritance 来解决某个问题,要么是 inheritance 带来了某些问题然后不得不创造新的概念,具体如何让我们拭目以待。

5.1 Classes, Superclasses and Subclasss

Inheritance 到底是为了啥?
To model “is-a” relationship.

5.1.1 Defining Subclasses

5.1.2 Overriding Methods

Note:
The difference between super and this:

  • this is a reference to the object itself, you can assign it to another object reference (后半句存疑).
  • super is keyword, it tells the compiler to invoke super class methods.

5.1.3 Subclass Constructors

Note:

  1. When used as constuctors, this and super are very similar, they must be put as the first statement of another constructor.
  2. In subclass constructors:
    1. 有 call superclass constructor 吗 ?
    2. Yes -> 3; No->4
    3. call superclass constructor and continue. End
    4. call superclass no-arg constructor.
    5. 有 superclass no-arg constructor 吗?
    6. Yes -> 7; No->8
    7. call superclass no-arg constructor and continue. End
    8. compiler error. End

Polymorphism: an object variable refer to multiple actual types.

5.1.4 Inheritance Hierarchies

5.1.5 Polymorphism

Substitution Princile:
You can use a subclass object whenever the program expects a superclass object.

Note:
superclass reference cannot be assigned assigned to subclass variable.

但是这一点似乎在 Array的时候出现的不同:

//Manager is a subclass of Employee
Manager m1 = new Manager();
Employee e1 = new Employee();
m1 = e1; // ERROR

e1 = m1; // OK
-----------------------------
//In the following case, it seems ok
Manager[] managers = new Manager[10];
Employee[] employees = new Employee[10];

employees = managers;
//Here employees also refer to the an array of manager objects.

employees[0] = new Employee();
//compiler不报错,他觉得没毛病啊,你不是说了是个 employee array 嘛。

managers[0].someOnlyManagerHasMethod();
//compiler不报错,他觉得没毛病啊老铁,你不是说了这个是 manager array 嘛。
// Solution to prevent such problem: ArrayStoreException

5.1.6 Understanding Method Calls

ClassC x;
x.f(args);

方法调用的时候到底发生了什么呢?

  1. Compiler 列出所有的 当前ClassC以及ClassC的supercalsses 里面可以调用的方法。
  2. 通过 args 进一步筛选出 methods。
  3. 如果 args 有 type conversion 那就全部先搞定。
  4. 如果找不到或者找到了许多个,那就报错。

Overriding
Subclasses 和 superclasses 有 signature一样的方法。(return type 不算 signature 的一部分哦,那 return type 不一样可以吗?还算 overriding 吗?算是算,但是你的 return type 也不能随便变,应该compatible,compatible意思无非就是必须是subclass。)

Wow. 居然存得有一个 class-method table,具体见 page 305

5.1.7 Preventing Inheritance: Final Classes and Methods

Note:

  1. final class will automatically make all the methods final
  2. but not the fields. The fields can still change after the obejct is constructed.

Inlining: Optimize the method calls when it is short and not overriden. 作者说现在的电脑里 Just-In-Time compiler 貌似已经解决了这问题了。

5.1.8 Casting

What
Casting: convert one type into another

Why:
作者认为,你只有一个地方需要 casting:to use an object in its full capacity after its actual type has been temporarily forgotten.
这句话是什么意思呢?意思是我们有一个 object,可能是 ClassA 的,在写代码的过程中一直被 cast 到 superclass。(注意,casting 到 lower class 是不被允许的。)到后面我们要用 ClassA 的 method 怎么办呢 (This is so called “actual type has been temporarily forgotten”)?这个时候就应该 downcasting。

5.1.9 Abstract Classes

作者的告诫:
Move common methods(no matter abstract or not) to higher level (no matter abstract or not.)

5.1.10 Protected Access

protected 具体有什么用?

  1. Only allow subclass access the methods
  2. Allow subclasses to access the private fields ( less common)

注意,这两点是分别对 fields 还有 methods 说的。而且作者专门提到,object 的 clone method 就是一个值得用 protected 的例子。这是为什么呢?

protected is also accessible to classes in the same package.
Java access modifier


5.2 Object: The Cosmic Superclass

5.2.1 Variables of Type Object

Interesting point:
Primitive types are not “objects” but the arrays of primitive types are objects.

5.2.2 The equals Method

// method1
return Objects.equals(a, b);

//method2
if(a == null && b == null) return true;
if(a == null || b == null) return false;
return a.equals(b);

//这两个在干一样的事情,什么事情呢?检查两个 objects 是不是一样的。Objects.equals()就是一个考虑了 null 情况的简便方法

5.2.3 Equality Testing and Inheritance

当 check 两个对象是不是一样的时候,我们很自然的会 check 他们是不是一个类。
一种做法是:

this.getClass() == that.getClass();

还有一种做法是:

that instanceof this.getClass();

作者认为第二种不是比较好的做法。因为 instanceof 是会承认 subclass 的,一个subclass 可以看做是 an instance of its superclass,这就导致了不对称性,即 a == b 但是 b != a。但是某些情况下,不同 class 的对象又可以是看做是一样的,比如两个排列不同的 set,按道理只要里面存储的elements 是一样的就应该是一样的。这种情况下,即便是 class 不一样也应该是一样的。

总结一下,作者认为:

  1. If subclasses can have their own notion of equality, then the symmetry requirement forces to use the getClass test.
  2. If the notion of equality is fixed at the superclass, then you can use the instanceof test and allow objects of different subclasses to be equal to one another.

小细节,小问题:

  1. 为啥用 Objects/Arrays 呢?为啥不是 Object/Array 呢?
    我猜测仅仅是为了把这些辅助性的 method 分开。

5.2.4 The hashCode Method

WHAT
什么是 hashcode?
It is an integer that is derived from the an object.

WHY
有什么用啊?
For objects that client might insert into a hashtable (discussed in chapter 9)

小细节,小问题:

  1. 原来 Objects.hashCode(double someDouble) 会生成一个 double 吗?
    看起来 是会生成一个 Double 对象,可能 是因为 autoboxing 的原因。
  2. 为什么 equalhashCode 必须要互相 compatible 呢?和 Insertion into hashtable 有关吗?

5.2.4 The toString Method

小细节,小技巧:

  1. "" + x seems like better than x.toString() because the former automatically calls toString() method and works with primitive types also.
  2. arrays also(same as primitive types) did not implement toString() method. so better use Arrays.toString()

5.3 Generic Array Lists

文章需要记住的点 Interesting Notes:

  1. 与 C/C++ 不同,Java 当中的 Array 是可以动态设置大小的。只是一旦设置之后就不可以再调整了。为了解决这一问题,我们发明了 ArrayList,这也是第一次接触到 Generic 的概念。
  2. 如何创建自己的 Generic 数据类型,不在本章的讨论范围以内。

5.3.1 Declaring Array Lists

文章需要记住的点 Interesting Notes:

  1. ArrayList<Employee> staff = new ArrayList<Employee>
    这样写不是很有效率吧,我们给编译器提供的信息重复了不是吗?为什么我需要告诉编译器两次,我到底需要什么样的 ArrayList 呢?所以为了更高效,我们有了下面的做法。
//方法一:
//这里可不能像方法二一样,省略掉 Employee。
var staff = new ArrayList<Employee>();

//方法二:
ArrayList<Employee> staff = new ArrayList<>();
  1. 这个 ArrayList 的特点就是,内存不够自动分配,但是自动分配的过程要求我们重新创建一个 Array,然后把旧的数据放到新的 Array 里面。这一过程用脚趾头想都知道是比较浪费的,所以要尽量避免这一过程。怎么避免呢?你先猜一个你要用的大小呗。staff.ensureCapacity(100);
  2. 除了节约CPU消耗,还应该节约内存(我看如今这个内存发展的速度,节约内存怕是意义不大吧),怎么办呢?trimToSize 就好了。就是告诉电脑不要预留空间了,我需要的空间已经固定了,后续我尽量不再加了。

5.3.2 Accessling Array List Elements

文章值得记住的点 Interesting Notes:

  1. 不可以用 [index] 来读取了哦,只能用 get set,(不过这是为什么呢?)
  2. set 和 add 是有区别的!add 用来添加,set 用来替换。(如果我非要用 set 来添加会发生什么呢?)
  3. Array 和 ArrayList 各有各的优点和好处,可以用 arrayList.toArray(someArray) 来进行转换。

5.3.3 Compatibility between Typed and Raw Array Lists

文章需要记住的点 Interesting Notes:
由于历史遗留问题,曾经的 ArrayList 是不用添加类型参数的,即不用写成 ArrayList<Employee>。这一章主要讲如何在这两种新老语法当中自由转化。

  1. 有类型参数的 ArrayList 可以赋值给没有参数的 ArrayList。但是反之却不可以。

  2. ArrayList<?> 会被转化成 raw ArrayList,他们在 runtime 环境下是一样的。

  3. 我们可以用 `@suppressWarnings(“unchecked”)


5.4 Object Wrappers and Autoboxing

文章需要记住的点 Interesting Notes:

  1. Wrapper class 是 immutable 的。(为什么要这么设计呢?上一次String immutable 的原因是为了节约资源,大部分人很少改String,这一次呢?)
  2. 当然了,由于创建了对象的关系,ArrayList 要远远比 int[] 低效。
  3. 看起来 Wrapper class 和一般的 primitive types 最大的区别在于,这两者中是怎么定义 “相等” 这个概念的。 Primitive types 可以很轻松的使用 ==,但是如果在 Wrapper 上使用吗 ==,可能就会直接比较 object reference 了。

5.5 Methods with a Variable Number of Parameters

文章需要记住的点 Interesting Notes:

  1. 在实现 variable number of parameters 的时候 Object... args is same as Object[] args (这个 parameter 必须要放在最后一个吗?)

5.6 Enumeration Classes

文章需要记住的点 Interesting Notes:

  1. Wow 其实可以这么理解枚举类:These classes have a fixed number of intances. 这是一个有固定数量实例的类。
  2. (可以用 == 来比较枚举类的实例?)

5.7 Reflection

文章需要记住的点 Interesting Notes:

  1. 什么是 relective:一个可以用来分析Java 类的各种能力的程序。看起来这大多是用来开发工具的,而不是用来开发应用的。

5.7.1 The Class class

文章需要记住的点 Interesting Notes:

  1. Runtime Type Identification(RTTI) 这玩意这么想可能比较好理解,当你调用 getClass() 方法的时候,返回的就是一个 Class 类的实例。
  2. 获得 Class 类实例(不要被Class的名字所忽略了,他本身就是一个类)的三种方法:
Employee e = new Employee();

Class c1 = e.getClass();
Class c2 = Class.forName(Employee);
Class c3 = e.class;

5.7.2 A Primer on Declaring Exceptions

文章需要记住的点 Interesting Notes:

  1. 如何理解两种 Exception?
    Checked Exception: 编译器希望,或者说要求程序员要么明确知道这个异常,要么提供了异常处理。
    Unchecked Exception:编译器实际希望你完全避免这种异常,而不是写一个处理器去处理它。

5.7.3 Resources

文章需要记住的点 Interesting Notes:

  1. Class 类的使用对于 resource loading 有帮助。
  2. resource loading 有什么用呢?这一点搞过一点点 安卓开发就明白,String 都不应该写死,不然就不好替换了。
  3. Class 类的实例都可以支撑一个 getResource 方法,用来获取某个 resource 的连接。

5.7.4 Using Reflection to Analyze the Capabilities of Classes.

文章需要记住的点 Interesting Notes:

  1. Field, Method, Constructor 还有这三类用来描述一个 Class。(除了让我们能够在不看源码的情况下得知一个某一个类的细节,还有什么用吗?)

5.7.5 Using Reflection to Analyze objects at Runtime

文章需要记住的点 Interesting Notes:

  1. 这里更加清晰地描绘了 reflection 有什么用:让你能够只知道某个对象的的 fields,哪怕你在compile time 的时候并不知情。(这也许是 Generic 的内核所在,可能我们需要对某个对象的 fields 进行读取或是调整,可是我们连这个对象有些什么 fields,有多少 fields 等等,都不知情。)
  2. 哪怕是 private 的 fields 也可以读取哦,我们可以很轻松的 override 这个设置。可惜即便是 setAccessible 也不是万能的,他本身也会被其他的东西override。
  3. ObjectAnalyzer 这个有什么用呢?主要就是在我们使用 toStrings() 帮助我们解决一些难题的小助手。(书中列有这个类的源码,但是暂时没有耐心读完,以后有空再读。)

5.7.6 Using Reflection to Write Generic Array Code

文章需要记住的点 Interesting Notes:

  1. 这个地方感觉非常的复杂让人困惑了。首先需要明确,我们想要做什么?我们想要实现一个方法,这个方法可以把任意类型的数组复制一遍,然后放到一个两倍大的数组里面。
  2. 实现这样的一个方法我们可能会面临什么样的挑战?
    Object[] 类的数组是不可以向下转型的。如果你有一个子类对象数组,暂时放在来一个 Object 类的数组里,然后再进行向下转型,这是可以的。但是如果数组一开始就是 Object[],是不可以向下转型的。
  3. 看起来 Array 以及 Arrays 两个类都在 Java库当中。有一个问题,问什么不用 a.length 直接获得长度呢?
  4. int[] 本身整个算作是一个对象,而且这玩意儿还不能转换成 Object [].

5.7.7 Invoking Arbitrary Methods and Constructors

文章需要记住的点 Interesting Notes:

  1. wow,由于 refletive 的存在,不仅可以获知一个类的 fields,还可以触发一个类的 methods。
  2. invoke(Object obj, Object… args) 第一个参数是传说中的 implicit parameter,就是通常所说的 this,目的在于告诉电脑,谁的 method 你想要触发呢?

5.8 Design Hints for Inheritance

文章需要记住的点 Interesting Notes:

  1. 不要用 protected fields,注意人家说的是 fields,没有说 methods。用在 methods 上的时候,他代表一个 method 还不适合通用,需要 subclass 修改一下。
  2. Reflection 会导致大量的程序错误,尽量少用。

Dictionary

Array 数组
Exception 异常
Generic 泛型
Primitive types 原始类型
Object reference 对象的引用
Runtime Type Identification(RTTI) 运行时类型识别
Varaible Number of Parameters:不等数量的参数
Wrapper Class 包装类

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Core Java Volume I–Fundamentals, 1 (11th Edition) By 作者: Cay S. Horstmann ISBN-10 书号: 0135166306 ISBN-13 书号: 9780135166307 Edition 版本: 11 出版日期: 2018-09-06 pages 页数: 928 The #1 Java Guide for Serious Programmers: Fully Updated for Java SE 9, 10 & 11 For serious programmers, Core Java, Volume I—Fundamentals, Eleventh Edition, is the definitive guide to writing robust, maintainable code. Whether you’re using Java SE 9, 10, or 11, it will help you achieve a deep and practical understanding of the language and API, and its hundreds of realistic examples reveal the most powerful and effective ways to get the job done. Cay Horstmann’s updated examples reflect Java’s long-awaited modularization, showing how to write code that’s easier to manage and evolve. You’ll learn how to use JShell’s new Read-Eval-Print Loop (REPL) for more rapid and exploratory development, and apply key improvements to the Process API, contended locking, logging, and compilation. In this first of two volumes, Horstmann offers in-depth coverage of fundamental Java and UI programming, including objects, generics, collections, lambda expressions, Swing design, concurrency, and functional programming. If you’re an experienced programmer moving to Java SE 9, 10, or 11, there’s no better source for expert insight, solutions, and code. Master foundational techniques, idioms, and best practices for writing superior Java code Leverage the power of interfaces, lambda expressions, and inner classes Harden programs through effective exception handling and debugging Write safer, more reusable code with generic programming Improve performance and efficiency with Java’s standard collections Build cross-platform GUIs with the Swing toolkit Fully utilize multicore processors with Java’s improved concurrency

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值