【读书笔记:疯狂java讲义】java面向对象

面向对象

面向对象3大特性

封装

继承

多态

图片参考:如何用一句话说明什么是面向对象思想?
这里写图片描述

java面向对象

3大特性在java中的体现

【封装】 : java提供了private,protected,和public 3个访问控制修饰符。

【继承】 : 提供了extends关键字让子类继承父类。

【多态】:子类对象 可直接赋值给 父类变量。

java中的对象相关的关键字

final 修饰符

语义

final修饰的变量获得初始值后不能被重新赋值

区分 final修饰成员变量局部变量

final 修饰成员变量
(1)final修饰的成员变量必须由程序员显示的初始化,系统不会对final成员进行隐式初始化。 (与普通成员变量不同的是)

(2)final修饰的类变量声明时静态初始化块中指定初始值

(3)final修饰的实例变量,在声明时非静态初始化块中或构造器中指定初始值

正确写法

class A{
    final int data = 0;//正确
}

错误写法

class A{
    final int data;//错误
}

final修饰的局部变量
系统不会对局部变量进行初始化局部变量必须由程序员显示初始化。因此使用final修饰局部变量时,(1)既可以在定义时指定默认值,也可以不指定默认值。(2)如果final 修饰的局部变量在定义时没指定默认值,则可以在后面的代码中对该fianl变量赋初始值,但只能一次,不能重复赋值。
正确写法:

    public static void main(String[] args) {
        final int data = 2;
        System.out.println(data);
    }

或者:

    public static void main(String[] args) {
        final int data ;
        data = 2;
        System.out.println(data);
    }

错误写法1:

    public static void main(String[] args) {
        final int data;
        System.out.println(data);//报错,使用之前未初始化data.(如果不使用,则不会报错)。该阶段由编译器检查。
    }

错误写法2:

    public static void main(String[] args) {
        final int data ;
        data = 2;
        data = 3; // 编译时报错,只能赋值一次。
        System.out.println(data);
    }

另外局部变量(无final 修饰情况)也必须被初始化

    public static void main(String[] args) {
        int data ;
        System.out.println(data);//报错
    }

区分:final修饰基本类型变量 和 修饰引用类型变量

final修饰基本类型变量】,不能对基本类型变量重新赋值,因此基本类型变量不能被改变。

final 修饰 引用类型变量】,它保存的仅仅是一个引用,final只保证这个引用类型变量所引用的地址不变,即一直引用同一个对象(使用final修饰的引用类型变量不能被重新赋值),但这个对象完全额可以发生改变(即可以改变引用类型变量所引用对象的内容)。

final方法

final修饰的方法不可被重写。如果不希望子类重写某个方法,可以使用final修饰该方法。

final类

final类不可以有子类(不可被继承)。

如:String类。

不可变类

使用private和final修饰符类修饰该类的成员变量。
提供带参数构造器
不提供setter方法
如果有必要,重写Objcet类的hashCode()和equals()方法。

缓存不可变类的实例 (TODO:实现)

如果程序经常需要使用相同的不可变类实例,则应该考虑缓存者在不可变类的实例。毕竟重复创建相同的对象没有太大的意义,而且加大系统开销。

抽象类

适用 的场景

某个父类 知道 子类 应该包含怎样的方法,但无法确切知道子类如何实现。
【举例】比如,父类 车能够行走(walk()),但是我们不能说明如何行走,只能在子类中去具体化,子类 汽车用轮子行走。

更具体的作用

抽象类是从多个具体类抽象出来的父类,具有更高的抽象层次。

抽象类一般作为子类的模板,从而避免了子类设计 的随意性

了解更多内容可参看模板模式:【菜鸟教程】模板模式

规则

关键字:

修饰对象: (1)类 ;(2)方法。

抽象类

abstract class Animal { //用abstract来定义一个Animal为抽象类
}

抽象方法

public abstract void go(); //用abstract来定义一个抽象方法 go.

抽象类 与 抽象方法

必须使用修饰符 abstract

抽象方法不能有方法体

抽象类不能被实例化。( 无法使用new关键字来创建实例 )

抽象类可包含成分】: Field、方法(普通方法及抽象方法)、构造器、初始化块、内部类、枚举类。

【抽象方法 与 抽象类关系】抽象方法只能被定义成抽象类

注意

【矛盾修饰】 static 与 abstract不能同时修饰方法。static方法是类的方法,没有所谓的类抽象方法

【矛盾修饰】private 与 abstract不能同时修饰方法。abstract修饰的方法必须被子类重写才有意义,而private则是拒绝子类重写,产生矛盾。所以不能同时修饰。

【区分:空方法 与抽象方法】

空方法

public void test(){}

抽象方法

public void test();//没有方法体。

更彻底的抽象 : 接口

主要思想】接口是从多个相似类中抽象出来的规范,接口不提供任何实现.接口体现的是规范和实现分离的哲学.

接口通常是定义多一组公用方法.

接口与抽象类的区别和联系

区别

参考:(接口与抽象类的区别

1.【继承角度】一个类可以实现多个接口 ,但却只能继承最多一个抽象类。

2.【抽象方法的纯粹性】抽象类可以包含具体的方法 , 接口的所有方法都是抽象的。

3.【成员变量的限制】抽象类可以声明和使用字段 ,接口则不能,但接口可以创建静态的final常量。

4.【方法的权限】接口的方法都是public的,抽象类的方法可以是public,protected,private或者默认的package;

5.【构造函数】抽象类可以定义构造函数,接口却不能。

6.【适用的场景的区别】(1)接口体现的是纯粹的规范(全为抽象方法)标准(类似数据库中的模式);(2)抽象类,体现了模板设计,是实现过程中的中间产品。(介于高度抽象的规范具体实现之间的一种中间形式

PS: 体会面向接口的设计思想

联系

实例化】接口与抽象类都不能被实例化。

抽象方法】都可以包含抽象方法。

内部类

内部类 (嵌套类): 一个类的定义 放在另一个类中。

内部类的作用

增强封装】 内部类提供了更好的封装, 可以把内部类隐藏在其外部类之内。外部类可控制外界对于内部类的访问。(例如:Cow类,需要组合一个CowLeg对象,而CowLeg只在Cow类中有效,这时就可以用内部类)

内部类的权限内部类可直接访问外部类的私有数据。但是,外部类不能访问内部类的一些实现细节

匿名内部类】适合于创建哪些仅需要一次使用的类。(如实现匿名监听器类)

非静态内部类

内部类属于某个对象

定义形式:

public class Cow{
    private class CowLeg{//非静态内部类

    }
}

静态内部类

该内部类属于外部类本身,而不是外部类的某个对象。

定义形式:

public class Cow{
    static class CowLeg{//非静态内部类

    }
}

局部内部类

如果把一个内部类在方法中定义,则该类为局部内部类

作用范围】仅在该方法中有效。因为局部内部类不能在除方法之外的地方使用,所以局部内部类不能使用 访问控制符 和static 修饰符修饰

【注意】一个类中可以有重名的局部内部类(在不同的方法中)。
举例:

public static void main(String[] args) {
         class CowLeg{   //定义局部内部类

        }

        Cowleg cl = new CowLeg();  //使用局部内部类
    }

匿名内部类

创建只需要使用一次的类,(使用该类创建一次实例)。

注意

不能为抽象类。

不能定义构造器。(因其没有类名,但可定义实例初始化块,通过这种形式完成构造器要做的事情

定义形式

new 父类构造器(实参列表)| 实现接口(){

    //匿名内部类类体部分
}

使用内部类

(1)在外部类内部 使用 内部类

和普通类的使用没有什么区别。唯一的区别是:不要在外部类的静态成员中使用非静态内部类,因为静态成员不能访问非静态成员

访问形式:

Cowleg cl = new CowLeg();  //在外部类内部使用 内部类

(2)在外部类以外 使用 非静态内部类
权限角度

使用private修饰的内部类】不能用private修饰内部类。(private修饰的内部类只能在外部类内部中使用

省略访问控制符的内部类】只能被 与外部类处于同一个包中 的其他类访问。

使用protected修饰的内部类】可访问者为:(1)与外部类处于同一个包中的其他类;(2)外部类的子类。

使用public修饰的内部类】任何地方均可访问。

使用形式

public class Cow{
    public class CowLeg{//非静态内部类

    }
}

在Cow外部访问 CowLeg:

Cow cow  = new Cow();
Cow.CowLeg cl = cow.new CowLeg(); // 依赖于Cow的实例。

(3)在外部类以外使用静态内部类

静态内部类 是 外部类类相关的, 因此创建内部类对象时 无需 创建外部类对象

使用形式

public class Cow{
    static class CowLeg{//非静态内部类

    }
}

在Cow外部使用CowLeg:

Cow.CowLeg cl =  new Cow.CowLeg();

闭包 与 回调

闭包

闭包是一种能被调用的对象,它保存了创建它的作用域信息

回调

允许客户类通过 内部类引用 来调用 其外部类的方法

闭包 为回调 提供了基础

注意
监听器模式,可以把监听器定义在被监听 的内部,就很好的体现了闭包与回调的思想

参考
回调函数(callback)是什么?

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值