Java面向对象编程高级(二)

在Java中,抽象类是一种不能被实例化的类,它主要用于为子类提供一个公共的类型以及可以共享的行为实现。抽象类中可以包含抽象方法(没有具体实现的方法)和非抽象方法(有具体实现的方法)。理解抽象类的概念及其用途对于深入学习Java面向对象编程至关重要。


抽象类 

什么是抽象类?

在Java编程语言中,abstract关键字用于定义抽象类抽象方法抽象类是不能直接实例化的类,它的存在主要是为了被继承。当你预计某些类的子类会有一些共同的属性行为,但这些行为的具体实现可能因子类而异时,使用抽象类就非常合适了

抽象方法 

抽象方法是一种没有具体实现的方法,它只有声明而没有方法体。抽象方法强制子类必须提供具体的实现。在抽象类中定义抽象方法的一般形式如下:

public abstract class AbstractClass {
    // 抽象方法
    public abstract void someMethod();
}
抽象类的介绍 
  1. 用abstract 关键字来修饰一个类时,这个类就叫抽象类  访问修饰符 abstract 类名{}
  2. 用abstract 关键字来修饰一个方法时,这个方法就是抽象方法,访问修饰符 abstract 返回类型 方法名(参数列表);//没有方法体
  3. 抽象类的价值更多作用是在于设计,是设计者设计好后,让子类继承并实现抽象类()
  4. 抽象类,是考官比较爱问的知识点, 在框架和设计模式使用较多
 定义抽象类

要定义一个抽象类,需要在类的声明前加上abstract关键字。抽象类中可以有抽象方法,也可以有非抽象方法。例如:

public abstract class Animal {
    String name;
    
    // 抽象方法
    public abstract void eat();
    
    // 非抽象方法
    public void sleep() {
        System.out.println("Zzz...");
    }
}
继承抽象类 

子类必须覆盖(实现)抽象类中的所有抽象方法,除非子类也是抽象类。这保证了抽象类中定义的接口在子类中得到了具体实现。例如:

public class Dog extends Animal {
    @Override
    public void eat() {
        System.out.println("Dog is eating.");
    }
}
为什么使用抽象类?
  1. 代码复用:抽象类可以提供一些通用的实现,子类可以重用这些实现,减少代码重复。
  2. 设计模式:在很多设计模式中,如模板方法模式,抽象类用于定义算法的骨架,而将一些步骤延迟到子类中实现。
  3. 强制一致性:通过要求子类实现特定的抽象方法,确保了所有子类都遵循某种通用的行为规范。
注意事项

  • 抽象类不能被实例化,即你不能创建一个抽象类的对象。
  • 如果一个类包含了至少一个抽象方法,那么这个类必须声明为抽象的。
  • 抽象方法在抽象类中可以不提供实现,但在非抽象子类中必须被实现。
抽象类使用的注意事项和细节讨论 
  • 抽象类不能被实例化
  • 抽家类不一定要包含abstract方法。也就是说,抽象类可以没有abstract方法[举
  • 一旦类包含了abstract方法,则这个类必须声明为abstract [说明]4) abstract只能修饰类和方法,不能修饰属性和其它的。
  • 抽象类可以任意成员【抽象类本质还是类】
  • 抽象方法不能有主体
  • 如果一个类继承了抽象类,则它必须实现抽象类的所有抽象方法,除非它自己也声明自己为abstract类
  • 抽象方法不能使用private,final和static来修饰

 接口

在Java编程语言中,接口(Interface)是一种定义行为的方式,它比抽象类更加抽象和灵活。接口中所有的方法默认都是抽象的(从Java 8开始,接口也可以包含默认方法静态方法),并且没有任何实现。接口主要用于多个不相关的类之间定义共同的行为标准,从而实现多态性。

基本介绍 

interface 接口名{

        //属性 

        //抽象方法
}

class 类名 implement 接口{

自己的属性

自己的方法

必须实现的接口的抽象方法 

}

定义接口 

定义接口的基本语法如下:

public interface MyInterface {
    // 常量声明
    int CONSTANT = 10;
    
    // 抽象方法声明
    void someMethod();
    
    // 从Java 8开始,可以有默认方法
    default void defaultMethod() {
        System.out.println("This is a default method.");
    }
    
    // 从Java 8开始,还可以有静态方法
    static void staticMethod() {
        System.out.println("This is a static method in an interface.");
    }
}

 

 实现接口

类通过使用implements关键字来实现接口。如果一个类实现了接口,就必须实现接口中所有的抽象方法(除非该类也是抽象类)。示例:

public class MyClass implements MyInterface {
    @Override
    public void someMethod() {
        System.out.println("Implementing the method defined in the interface.");
    }
}

 

接口的多重继承 

 Java中的类只能单一继承,但可以实现多个接口,这使得接口成为实现多重继承功能的有效方式。例如:


interface InterfaceA {
    void methodA();
}

interface InterfaceB {
    void methodB();
}

class MyClass implements InterfaceA, InterfaceB {
    @Override
    public void methodA() {
        // 实现代码
    }

    @Override
    public void methodB() {
        // 实现代码
    }
}

接口注意事项和细节 
  • 接口不能被实例化
  • 接口中所有的方法是 public 方法, 接口中抽象方法,可以不用 abstract 修饰 .一个普通类实现接口,就必须将该接口的所有方法都实现,可以使用 alt+enter 来解决
  • 抽象类去实现接口时,可以不实现接口的抽象方法

使用接口的好处 
  1. 设计原则:接口遵循了设计模式中的“面向接口编程”原则,降低了模块间的耦合度。
  2. 多态性:实现了接口的类可以被向上转型为接口类型,增加了程序的灵活性和可扩展性。
  3. 代码重构与维护:接口定义了行为规范,方便未来对代码进行重构和维护,不影响已有的实现类。
  4. 实现多重继承:虽然Java类不支持多重继承,但通过接口可以达到类似的效果。

内部类 

Java中的内部类(Inner Class)是指在一个类的内部定义的另一个类。内部类提供了更好的封装性、访问外部类的成员以及实现复杂逻辑的能力。根据它们的定义位置和作用域的不同,Java内部类主要分为四种类型:成员内部类局部内部类匿名内部类静态嵌套类。下面是对这四种内部类的详细介绍和示例。

成员内部类

成员内部类是最常见的内部类形式,它是外部类的一个成员,如同外部类的字段和方法一样。它可以访问外部类的所有成员,包括私有成员。 

public class OuterClass {
    private int data = 10;
    
    // 成员内部类
    class InnerClass {
        void display() {
            System.out.println("Data from outer class: " + data);
        }
    }
    
    // 方法中创建内部类实例并调用
    public void showInner() {
        InnerClass inner = new InnerClass();
        inner.display();
    }
}
局部内部类 

局部内部类是在方法或代码块中定义的类,它的作用域仅限于该方法或代码块。

public class Outer {
    void someMethod() {
        class LocalInner {
            public void show() {
                System.out.println("This is a local inner class.");
            }
        }
        
        LocalInner li = new LocalInner();
        li.show();
    }
}
局部内部类的使用 

说明:局部内部类是定义在外部类的局部位置,比如方法中,并且有类名。

1.可以直接访问外部类的所有成员,包含私有的
2.不能添加访问修饰符,因为它的地位就是一个局部变量。局部变量是不能使用
修饰符的。但是可以使用final 修饰,因为局部变量也可以使用final
3.作用域:仅仅在定义它的方法或代码块中。
4.局部内部类﹣-﹣访问﹣--->外部类的成员[访问方式:直接访问]
5.外部类﹣-﹣访问﹣--->局部内部类的成员,访问方式:创建对象,再访问(注意:必须在作用域内)记住:(1)局部内部类定义在方法中/代码块
                             (2)作用域在方法体或者代码块中
                             (3)本质仍然是一个类
6.外部其他类﹣-﹣不能访问﹣---->局部内部类(因为 局部内部类地位是一个局部变量)
7.如果外部类和局部内部类的成员重名时,默认遵循就近原则,如果想访问外部类的成员,则可以使用 (外部类名.this.成员)去访问 ,System.out.println("外部类的n2=" +外部类名.this.n2);

 匿名内部类

匿名内部类没有名字,通常用来创建某个类的子类实例,且只使用一次。它常用于实现接口或继承父类。

interface MyInterface {
    void doSomething();
}

public class Test {
    public static void main(String[] args) {
        MyInterface obj = new MyInterface() {
            @Override
            public void doSomething() {
                System.out.println("Doing something...");
            }
        };
        obj.doSomething();
    }
}
 静态嵌套类

静态嵌套类(也称为静态内部类)与成员内部类的主要区别在于它不依赖于外部类的实例,可以独立存在。它类似于普通的类,只是碰巧位于另一个类的内部。

public class OuterClass {
    static class StaticNestedClass {
        void display() {
            System.out.println("I am a static nested class.");
        }
    }
}

public class Main {
    public static void main(String[] args) {
        OuterClass.StaticNestedClass nestedObj = new OuterClass.StaticNestedClass();
        nestedObj.display();
    }
}

 内部类的使用场景
  • 封装性增强:内部类可以访问外部类的私有成员,但外部类无法访问内部类的实现细节,增强了封装性。
  • 逻辑组织:当一个类的实现细节仅对另一个类有意义时,可以使用内部类。
  • 事件监听和回调函数:匿名内部类广泛应用于实现事件监听器等场景,简化代码结构。
  • 单例模式:静态嵌套类常用于实现线程安全的单例模式

掌握Java内部类的使用,能够让你编写出更加灵活、结构更加清晰的代码。 

下期预告--》单例设计模式 

 

 

 

 

 

  • 17
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值