前言
本章将对面向对象剩下的一块东西进行讲解,抽象类,接口,内部类
范例
1.抽象方法和抽象类(该概念一般项目中不常用,都用接口)
通常来说,我们定义一个父类的时候,其中的方法我们没有想好该如何去实现,那么就用到了抽象方法的概念,我们可以定义这个方法为抽象方法,由子类自己去进行相关的实现。
语法: abstract 返回值类型 方法名(参数);
//定义抽象方法
public abstract void use();
相应的,包含抽象方法的类就是抽象类(抽象类中可以有普通方法)
语法:abstract 修饰符 class 类名
//定义抽象类
abstract class Tool{
String name;
//定义抽象方法
public abstract void use();
public void test(){
System.out.println("这是普通方法");
}
}
继承抽象类的非抽象类子类必须实现父类的相应抽象方法。抽象类不能被实例化。但可以向上转型,即父类引用指向子类对象。
2.接口(重要,项目中肯定用)
大家可以这么理解,接口就是比抽象类还抽象的类,其中定义的方法全部都是没有进行实现的方法,即都是抽象的。这一点和抽象类有很大不同,抽象类中允许有普通方法,接口则不允许。
语法:interface 接口名称 extends 【父接口1,父接口2…】{抽象方法集合} 注意:该处的抽象方法不需要标明abstract关键字。
package com.jwang.test;
public interface MyInterface {
public void play();
public void eat();
}
定义接口的详细说明:
- 访问控制符:只能是public 或 默认
- 接口名:和类名采用相同命名机制
- extends:接口可以多继承
- 常量:接口中的属性只能是常量,由public static final修饰,不写即默认
- 方法:接口中的方法都是抽象方法,都是 public abstract修饰,不写默认
要点:
- 子类通过implements来实现接口中的规范
- 接口不能创建实例,但是可以声明引用变量类型
- 一个非抽象类实现了接口,必须实现其中的所有方法,方法的访问控制只能是public
- jdk1.7之前,接口中只能包含静态常量和抽象方法,不能有普通属性和方法以及构造方法
接口的使用还是比较有难度的,需要我们自己去在以后的工作中深刻去理解面向接口的编程思想。
3.内部类
java中,内部类主要分为成员内部类(非静态内部类,静态内部类)、匿名内部类、局部内部类(基本不用)。
(1)非静态内部类
- 非静态内部类必须寄存在一个外部类对象里。因此,如果有一个非静态内部类对象那么一定存在对应的外部类对象
- 非静态内部类可以直接访问外部类的成员,但是外部类不能直接访问非静态内部类成员
- 非静态内部类不能有静态方法、静态属性以及静态初始化块
- 外部类的静态方法,静态代码块不能直接访问非静态内部类,包括不能使用非静态内部类定义变量、创建实例
package com.wdxx.conn;
public class Ref {
public static void main(String[] args) {
//声明内部类对象
A.B b = new A().new B();
b.show();
}
}
//外部类A
class A {
private String name = "约翰";
//内部类B
class B{
private int age = 10;
public void show(){
//调用外部类属性
System.out.println(A.this.name);
}
}
public void play(){
System.out.println(this.name);
}
}
(2)静态内部类
- 当一个静态内部类对象存在,并不一定存在对应的外部类对象。因此,静态内部类的实例方法不能直接访问外部类的实例方法和属性
- 静态内部类看作是外部类的一个静态成员。因此,外部类中可以通过静态内部类.名字的方式访问静态内部类的静态成员,通过new 静态内部类()访问静态内部类的实例
package com.wdxx.conn;
public class Ref {
public static void main(String[] args) {
//声明内部类对象
A.B b = new A.B();
b.show();
}
}
//外部类A
class A {
private String name = "约翰";
//内部类B
static class B{
private static int age = 10;
public void show(){
System.out.println(B.age);
}
}
public void play(){
//访问静态内部类的静态属性
System.out.println(B.age);
}
}
(3)匿名内部类
- 适合那种只需要使用一次的类。比如:键盘监听操作
- 匿名内部类没有访问修饰符
- 匿名内部类没有构造方法。因为它连名字都没有,哈哈哈
package com.wdxx.conn;
public class Ref {
public static void main(String[] args) {
Ref fRef = new Ref();
fRef.test(new A(){
@Override
public String show() {
return super.show();
}
});
}
public void test(A a){
System.out.println(a.show());
}
}
abstract class A{
public String show(){
return "aaa";
}
}
(4)局部内部类
- 定义在方法内部,仅供方法使用
- 实际开发几乎没有
package com.wdxx.conn;
public class Ref {
public static void main(String[] args) {
Ref.test();
}
public static void test(){
class A{
private String name = "局部内部类";
public String getName(){
return this.name;
}
}
System.out.println(new A().getName());
}
}