《Think in Java》
chapter 1 对象导论
面向对象程序设计(Object-oriented Programming ,OOP)
chapter 2 一切都是对象
字段和方法
若类的某个成员变量是基本数据类型,即是没有进行初始化,java也会确保它获得一个默认值。
局部变量没有默认值,必须初始化。
方法、参数和返回值
static 关键字
chapter 3 操作符
import static 是导入这个类中的静态方法,然后调用静态方法就可以直接用方法名,而不用"类名.",但要注意导入的方法名有相同的调用时会报错。
java操作符
String 类支持“+”和“+=”。
优先级
关系操作符
对于引用型数据,==和!=比较的是对象的引用,基本类型数据可以直接比较值。equals()可以比较引用型数据的值,equals方法内部是将引用型数据的值转换为基本类型并用== 比较。
字符串操作符
如果表达式以一个字符串起头,那么后续所有操作数都必须是字符串型。
类型转换操作符
chapter 4 控制执行流程
逗号操作符
for循环中用到逗号操作符。
for(int i=1,j=i+10;i<5;i++,j=i*2) {
System.out.println("i="+i+",j="+j);
}
Foreach 语法
for(float x : f){} //f是一个数组或集合,x是其元素类型。
标签和goto
Java需要使用标签的原因就在于有循环嵌套的存在。Java中没有goto语法,但它是java的一个保留字。
chapter 5 初始化与清理
默认构造器
如果你写的类中没有构造器,则编译器会自动帮你创建一个默认构造器。如果已经定义了一个构造器(无论是否有参数),编译器就不会帮你自动创建默认构造器。
this关键字
this关键字只能在方法内部使用,表示对“调用方法的那个对象”的引用。
在构造器中调用构造器
构造器中只能调用一个构造器,语句必须置于构造器第一句。
构造器只能被构造器调用,不能被其他任何方法调用。
清理:终结处理和垃圾回收
终结条件
class Book{
boolean checkedOut=false;
Book(boolean checkOut){
checkedOut=checkOut;
}
void checkIn() {
checkedOut=false;
}
protected void finalize() throws Throwable {
if(checkedOut) {
System.out.println("Error:checked out");
}
}
}
public class TerminationCondition {
public static void main(String[] args) {
Book novel = new Book(true);
novel.checkIn();
new Book(true); //while(true){new Book(true);}
System.gc(); //
}
}
垃圾回收器如何工作
引用计数:
class TestA{
public TestB b; }
class TestB{
public TestA a;
}
public class Main{
public static void main(String[] args){
A a = new A();
B b = new B();
a.b=b; //循环引用
b.a=a;
a = null;
b = null;
}
}
停止——复制
标记——清扫
成员初始化
方法的局部变量必须初始化才能操作。类的数据成员是基本类型,都会默认赋予初始值。类中对象引用未被初始化,会被设置为null。
指定初始化
- 直接提供初值 int i=99;
- 创建对象并初始化 Depth d=new Depth();
- 通过调用方法提供初值 int i= fun(); int fun(){ return 11; };
构造器初始化
构造器初始化发生在自动初始化(类成员的默认值)之后,构造器初始化实际上是覆盖了字段的默认值。
类中,变量定义的先后顺序决定了初始化顺序,但都会在构造器执行之前初始化。
静态数据初始化
显示的静态初始化
非静态实例初始化
{}代码块在构造器之前执行。
数组初始化
定义数组:int[] a1;
定义并初始化:int[] a1=new int[5]; 元素会被自动赋予默认值。
定义数组并初始化:int[] a1={1,2,3,4,5}; 元素手动赋予初值。
数组是一种特殊的对象:
String y="df";
int[] a1= {2,3,4};
System.out.println(a1.getClass().getName()); // [I
System.out.println(y.getClass().getName()); // java.lang.String
打印出的对象名是‘[I’。[表示数组,后面紧跟的数组的类型。
数组对象具有唯一固有成员length。
可变参数列表
printArray(对象1,对象2,对象3);
指定了可变参数,编译器会自动传入的参数列表转换为一个数组,省去显示地编写数组语法。
枚举类型
enum可以在switch语句内使用。
chapter 6 访问权限控制
public、protected、默认空、private
chapter 7 复用类
调用main方法:
初始化基类
继承体系中,构造器中第一行隐式调用父类无参构造器。
名称屏蔽
@Override 注解 表示该方法是重写的方法,如果不存在重写编译器就会报错。
protected 关键字
向上转型
final关键字
final数据
空白final
private final int j; 必须在域的定义处或每个构造器中用表达式对final字段赋值。
final 参数
Java 允许在参数列表中以声明的方式将参数指明为final。这意味着你无法在方法中更改参数引用所指向的对象。
final 方法
final 和 private 关键字
final 修饰方法无法被子类重写。
private 修饰方法无法被子类重写(必须通过添加@Override来验证),但子类可以存在和父类同名的private修饰的方法,但该方法不是从父类继承来的。
public class A {
final int i;
public A() {
i=4;
}
public final void fun1() {
System.out.println(" A fun1");
}
private final void fun2() {
System.out.println(" A fun2");
}
public void lfun3() {
fun3();
}
private void fun3() {
System.out.println(" A fun3");
} }
package cn.test; public class B extends A{
int i;
private int b; public void fun2() {
System.out.println(" B fun2");
} public void fun3() { //如果给该方法添加@Override,将报编译错误。
System.out.println(" B fun3");
} }
package cn.test; public class TestExtends {
public static void main(String[] args) {
B b = new B(); b.fun3();
b.lfun3();
}
}
final 类
final 修饰类,无法被继承。final类中的方法隐式指定为final的。
初始化及类的加载
继承与初始化(P147)
chapter 8 多态
package cn.test;
enum Note{
MIDDLE_C,C_SHARP,B_FLAT;
}
class Instrument{
public void play(Note n) {
System.out.println("Instrument.play");
}
}
class Wind extends Instrument{
public void play(Note n) {
System.out.println("Wind.play "+ n);
}
}
public class Music {
public static void tune(Instrument i) {
i.play(Note.MIDDLE_C);
}
public static void main(String[] args) {
Wind flute = new Wind();
tune(flute); //Upcasting
}
}
方法调用绑定
前期绑定
后期绑定
产生正确的行为
动态绑定
可扩展性
class Derived extends PrivateOverride{
public void f() {
System.out.println("public f()");
}
}
public class PrivateOverride {
private void f() {
System.out.println("private f()");
}
public static void main(String[] args) {
PrivateOverride po = new Derived();
po.f(); //打印:private f()
}
}
缺陷:域与静态方法
package cn.test;
class Super{
public int field=0;
public int getField() {return field;}
}
class Sub extends Super{
public int field=1;
public int getField() {return field;}
public int getSuperField() {return super.field;}
}
public class FieldAccess {
public static void main(String[] args) {
Super sup=new Sub();
System.out.println("sup.field="+sup.field+
",sup.getField()="+sup.getField());
Sub sub=new Sub();
System.out.println("sub.field="+sub.field+
",sup.getField()="+sub.getField()+
",sub.getSuperField()="+sub.getSuperField());
}
}
// sup.field=0,sup.getField()=1
// sub.field=1,sup.getField()=1,sub.getSuperField()=0
如果某个方法时静态的,它的行为就不具有多态性。
静态方法是与类,而并非与单个的对象相关联。
继承与清理(P295)
构造器内部的多态方法的行为
协变返回类型(P164)
package cn.test;
class Grain{
public String toString() {
return "Grain";
}
}
class Wheat extends Grain{
public String toString() {
return "Wheat";
}
}
class Mill{
Grain process() {
return new Grain();
}
}
class WheatMill extends Mill{
Wheat process() {
return new Wheat();
}
}
public class CovariantReturn {
public static void main(String[] args) {
Mill m = new Mill();
Grain g = m.process();
System.out.println(g);
m=new WheatMill();
g=m.process();
System.out.println(g);
}
}
用继承进行设计
package cn.test;
class Actor{
public void act() {};
}
class HappyActor extends Actor{
public void act() {
System.out.println("HappyActor");
}
}
class SadActor extends Actor{
public void act() {
System.out.println("SadActor");
}
}
class Stage{
private Actor actor = new HappyActor();
public void change() {actor=new SadActor();}
public void performPlay() {actor.act();}
}
public class Transmogrify {
public static void main(String[] args) {
Stage stage = new Stage();
stage.performPlay();
stage.change();
stage.performPlay();
}
}
纯继承与扩展
向下转型与运行时类型识别
chapter 9 接口
抽象类和抽象方法
关于编译时和运行时:
ConstantFolding.java文件:
public class ConstantFolding {
static final int number1=7;
static final int number2=4;
static int number3=2;
static int number4=8;
public static void main(String[] args) {
int product1=number1*number2;
int product2=number3*number4;
}
}
ConstantFolding.class反编译出的java文件:
// Decompiled by Jad v1.5.8e2. Copyright 2001 Pavel Kouznetsov.
// Jad home page: http://kpdus.tripod.com/jad.html
// Decompiler options: packimports(3) fieldsfirst ansi space
// Source File Name: ConstantFolding.java
public class ConstantFolding
{
static final int number1 = 7;
static final int number2 = 4;
static int number3 = 2;
static int number4 = 8; public ConstantFolding()
{
} public static void main(String args[])
{
int product1 = 28;//可见 number1*number2 在编译时处理的。
int product2 = number3 * number4; } }
接口(P172)
接口中的成员变量隐式地加上了static和final。
完全解耦(P174)
通过继承类扩展接口
接口可以继承接口
interface C extends A,B{ } //B,C是接口
组合接口时的名字冲突
适配接口(P181)
接口中的域
接口中的全局变量默认且必须是 static 和 final 的。修饰符自动是 public。
public interface Months {
int JANUARY=1,FEBRUARY=2,MARCH=3,APRIL=4,MAY=5,JUNE=6,
JULY=7,AUGUST=8,SEPTEMBER=9,OCTOBER=10,NOVEMVER=11,DECEMBER=12;
}
可以反编译Months.class,所有字段都自动添加 public static final ~
初始化接口中域
接口中定义的域不可以是“空final”,但可以使用非常量表达式初始化。
由于是static修饰,在类第一次加载时初始化。
嵌套接口
接口与工厂
《Think in Java》的更多相关文章
- 【书海】《Head First Java》 ——读后总结
<Head First Java> 中文版 (第二版) IT`huhui前言录 <Head First Java>这本书我不算特别细的看了一遍.认为十分适合初学者,甚至是没接触 ...
- 《Play for Java》学习笔记(一)项目框架
从今天开始认真复习<Play for JAVA>,该书以一个案例为主线,以前为应付项目马马虎虎看了一遍,好多地方都不明白!现在跟着这本书再走一遍,认真模拟,当做一个项目啦!! 一.Play ...
- 我本人一直以来犯的错误,在看了《Think In Java》后才抓了出来(转)
也许你是只老鸟,也许你的程序编的很精,但是,在你的程序生活,你也许没有注意到一些“常识性”的问题,因为有些时候我们不需要去注意,我们的程序 照样能够运行得飞快,但是如果那天有一个无聊的人问你一个像这样 ...
- 《图书管理系统——java》
/* (程序头部凝视開始) * 程序的版权和版本号声明部分 * Copyright (c) 2011, 烟台大学计算机学院学生 * All rights reserved. * 文件名: < ...
- 《Thinking in Java》 And 《Effective Java》啃起来
前言 今天从京东入手了两本书,<Thinking in Java>(第四版) 和 <Effective Java>(第二版).都可以称得上是硬书,需要慢慢啃的,预定计划是在今年 ...
- 读书笔记 之《Thinking in Java》(对象、集合)
一.前言: 本来想看完书再整理下自己的笔记的,可是书才看了一半发现笔记有点多,有点乱,就先整理一份吧,顺便复习下前面的知识,之后的再补上. 真的感觉,看书是个好习惯啊,难怪人家说"书籍是人类 ...
- 《Head First Java》读书笔记(1) - Java语言基础
<Head First Java>(点击查看详情) 1.写在前面的话 这本书的知识点说实话感觉有点散乱,但是贵在其将文字转换成了生动和更容易接受的图片,大量的比喻让人感受到了知识点的有趣之 ...
- D1——初读《Head First Java》
今天随便看了点<Head First Java>,发觉这本书的风格真是有趣.打算先把这本书踏踏实实的看了.学习切忌好高骛远.心浮气躁,尤其入门基础阶段更应该踏踏实实地学习知识.下面随便谈谈 ...
- 《Thinking In Java》阅读笔记
<Thinking In Java>阅读笔记 前四章:对象导论. 一切都是对象. 操作符. 控制执行流程 public在一个文件中只能有一个,可以是一个类class或者一个接口interf ...
- 读书笔记 之《Thinking in Java》(对象、集合、异常)
一.前言 本来想看完书再整理下自己的笔记的,可是书才看了一半发现笔记有点多,有点乱,就先整理一份吧,顺便复习下前面的知识,之后的再补上. 真的感觉,看书是个好习惯啊,难怪人家说“书籍是人类进步的阶梯” ...
随机推荐
- git 批量删除本地分支
git branch | grep 'bug' |xargs git branch -D
- selenium -文件上传的实现 -对于含有input element的上传
使用selenium做自动化时,我们经常会遇到的一个让人头疼的问题就是文件上传. 问题的难点在于selenium无法识别并操作Windows窗口,若我们可以绕过弹出框直接把文件信息上传给选择按钮,难点 ...
- BGP基本配置的方法
边界网关协议(BGP)是运行于 TCP 上的一种自治系统的路由协议. BGP 是唯一一个用来处理像因特网大小的网络的协议,也是唯一能够妥善处理好不相关路由域间的多路连接的协议. as100 as200 ...
- C++深度解析教程学习笔记(6)对象的构造和销毁
1. 对象的初始化 (1)从程序设计的角度看,对象只是变量,因此: ①在栈上创建对象时,成员变量初始化为随机值 ②在堆上创建对象时,成员变量初始化为随机值 ③在静态存储区创建对象时,成员变量初始化为 ...
- bash shell笔记2 结构化命令
二.使用结构化命令 知识内容: # 改变命令流 # 使用if-then逻辑 # 嵌套if-then # 测试条件 # 高级if-then功能 许多程序在脚本命令之间需要某些逻辑控制流,有些命令允许脚本 ...
- 在java中RandomAccessFile类的作用:对指定文件可以进行读写的操作
- pyspider用PyQuery解析页面数据
示例说明: 本示例主要是PyQuery解析返回的response页面数据.response.doc解析页面数据是pyspider的主要用法,应该熟练掌握基本使用方法.其他返回类型示例见后续文章. py ...
- HTML中 .clearfix:after的使用
将一个<div>标签随着内容的增加而增加
- java基础之io流总结四:字符流读写
字符流读写只适用于字符文件. 基本字符流(转换流)读写文件 转换流本身是字符流,但是实例化的时候传进去的是一个字节流,所以叫做转换流 InputStreamReader isr = new Input ...
- docker-compose之Nginx+Tomcat代理配置
Tomcat镜像制作与启动 Dockerfile如下 FROM docker.io/sssllc/centos7.-jdk1. #update RUN yum -y update; yum clean ...