Java 中的 封装、继承、多态

今天我们来聊聊 Java 面向对象的三大特性,封装、继承、多态

一、封装(Encapsulation)

定义: 封装是面向对象的基础特性,核心是 将对象的属性(数据)和行为(方法)捆绑在一起,并隐藏内部实现细节,只对外暴露可控的接口。

**类比:**手机的内部电路(属性)和通话功能(方法)被封装在外壳里,你不需要知道内部原理,只需通过按键 / 屏幕(接口)操作即可。

作用:

  • 提高代码安全性:防止外部随意修改对象的核心属性;
  • 增强可维护性:内部实现修改时,只要接口不变,外部代码无需调整;
  • 降低耦合:外部仅依赖接口,不依赖内部细节。

示例代码:

java 复制代码
// 封装的典型实现:属性私有化 + 提供get/set方法
public class Person {
    // 1. 属性私有化(private),隐藏内部数据
    private String name;
    private int age;

    // 2. 提供公共的getter(读取)/setter(修改)方法,控制访问规则
    public String getName() {
        return name;
    }

    public void setName(String name) {
        // 可以在setter中添加校验逻辑,保证数据合法性
        if (name == null || name.trim().isEmpty()) {
            throw new IllegalArgumentException("姓名不能为空");
        }
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        // 限制年龄范围,避免非法值
        if (age < 0 || age > 150) {
            throw new IllegalArgumentException("年龄必须在0-150之间");
        }
        this.age = age;
    }

    // 封装行为:对外暴露的业务方法
    public void introduce() {
        System.out.println("我叫" + name + ",今年" + age + "岁");
    }
}

// 测试
public class EncapsulationTest {
    public static void main(String[] args) {
        Person person = new Person();
        // 通过setter设置属性(会触发校验)
        person.setName("张三");
        person.setAge(25);
        person.introduce(); // 输出:我叫张三,今年25岁
    }
}

二、继承(Inheritance)

定义: 继承是面向对象的扩展特性,核心是 子类(Subclass)继承父类(Superclass)的属性和方法,实现代码复用,同时子类可以扩展或重写父类的功能

类比:"小狗" 和 "小猫" 都是 "动物",可以继承 "动物" 的属性(名字)和方法(吃东西、睡觉),再各自扩展特有功能(小狗是 "汪汪叫",小猫是 "喵喵叫")。

作用:

  • 代码复用:避免重复编写相同的属性和方法;
  • 体系化管理:构建类的层级关系;
  • 为多态奠定基础。

示例代码:

java 复制代码
// 父类:抽象的"动物"
public class Animal {
    // 父类属性
    protected String name; // protected:子类可直接访问

    // 父类构造方法
    public Animal(String name) {
        this.name = name;
    }

    // 父类方法
    public void eat() {
        System.out.println(name + "在吃食物");
    }

    // 父类方法
    public void sleep() {
        System.out.println(name + "在睡觉");
    }
}

// 子类:Dog(继承Animal)
public class Dog extends Animal {
    // 子类特有属性
    private String breed; // 品种

    // 子类构造方法:必须通过super调用父类构造
    public Dog(String name, String breed) {
        super(name); // 调用父类的构造方法
        this.breed = breed;
    }

    // 重写(Override)父类方法:扩展/修改父类行为
    @Override
    public void eat() {
        System.out.println(name + "(" + breed + ")在啃骨头");
    }

    // 子类特有方法:扩展父类功能
    public void bark() {
        System.out.println(name + "在汪汪叫");
    }
}

// 测试
public class InheritanceTest {
    public static void main(String[] args) {
        Dog dog = new Dog("旺财", "金毛");
        // 继承父类的方法
        dog.sleep(); // 输出:旺财在睡觉
        // 重写后的方法
        dog.eat(); // 输出:旺财(金毛)在啃骨头
        // 子类特有方法
        dog.bark(); // 输出:旺财在汪汪叫
    }
}

三、多态(Polymorphism)

定义: 多态是面向对象的核心特性,核心是 同一个行为(方法调用),不同对象表现出不同的形态。

**类比:**同样是 "吃" 这个行为,狗啃骨头、猫吃鱼、人吃饭,行为的具体实现不同,但对外的调用方式一致。

前提:

  • 存在 继承 / 实现关系(子类继承父类,或类实现接口);
  • 子类重写父类的方法;
  • 父类引用指向子类对象(Animal animal = new Dog())。

作用:

  • 提高代码灵活性:无需关注具体子类类型,统一调用父类方法即可;
  • 增强可扩展性:新增子类时,无需修改原有调用逻辑;
  • 降低代码耦合:调用方仅依赖父类 / 接口,不依赖具体子类。

示例代码:

java 复制代码
// 基于上面的Animal和Dog,新增Cat子类
public class Cat extends Animal {
    public Cat(String name) {
        super(name);
    }

    // 重写eat方法
    @Override
    public void eat() {
        System.out.println(name + "在吃小鱼干");
    }

    // 子类特有方法
    public void meow() {
        System.out.println(name + "在喵喵叫");
    }
}

// 测试
public class PolymorphismTest {
    // 统一的调用方法:接收Animal类型(父类),无需关心具体是Dog还是Cat
    public static void feedAnimal(Animal animal) {
        animal.eat(); // 运行时会根据实际对象类型调用对应方法(动态绑定)
    }

    public static void main(String[] args) {
        // 1. 父类引用指向子类对象
        Animal animal1 = new Dog("旺财", "金毛");
        Animal animal2 = new Cat("咪宝");

        // 2. 同一个方法调用,表现不同行为(多态核心)
        feedAnimal(animal1); // 输出:旺财(金毛)在啃骨头
        feedAnimal(animal2); // 输出:咪宝在吃小鱼干

        // 3. 多态的局限:父类引用不能直接调用子类特有方法,需强制类型转换
        // animal1.bark(); // 编译错误
        if (animal1 instanceof Dog) { // 判断对象实际类型
            Dog dog = (Dog) animal1; // 强制转换
            dog.bark(); // 输出:旺财在汪汪叫
        }
    }
}

总结:

  • 封装不止是属性私有化:类的 私有方法、内部类 也是封装的体现,目的都是隐藏内部逻辑。
  • Java 是单继承: 一个子类只能继承一个父类,但可以通过 "实现接口" 间接实现多继承效果。
  • 多态,对于成员方法,是 "编译看左边,运行看右边" ,即编译时检查父类是否有该方法,运行时执行子类重写的方法。而对于成员变量,则是 "编译和运行都看左边",访问的是父类中的变量。

心定则安,守拙成巧。-- 烟沙九洲

相关推荐
腻害兔1 小时前
【若依项目-产品经理视角】RuoYi-Vue-Pro 源码拆解:字典、短信、邮件、通知——后台系统的“基础设施四件套“!
java·前端·vue.js·产品经理·ai编程
碎光拾影1 小时前
ARM交叉工具链各工具作用及IMX6ULL平台LED+蜂鸣器裸机程序实现
java·开发语言·数据库
Miao121312 小时前
微服务 API 测试实践:海外某民宿平台如何构建模式驱动测试基础设施
java·开发语言
腻害兔2 小时前
【若依项目-产品经理视角】RuoYi-Vue-Pro 源码拆解:支付模块 yudao-module-pay,一个让产品经理都看懂的支付中台设计
java·前端·vue.js·产品经理·ai编程
CRMEB系统商城3 小时前
开源自建还是SaaS订阅?算一笔3年经济账
java·大数据·开发语言·开源
keyipatience4 小时前
线程栈与TLS和线程互斥
java·linux·服务器·开发语言·ubuntu
weixin_408099675 小时前
2026 图片去水印 API 接口完全指南:一键去除图片水印(附 Python/Java/PHP/C# 示例)
java·python·php·图片处理·api调用·图片去水印·石榴智能
钱六两5 小时前
#3、SpringAI 接入deepSeek大模型(喂饭版)
java·spring boot·ai编程
null_177 小时前
IntelliJ IDEA 极致流畅配置方案:Ultra 9 285K + 64GB 内存实测
java·ide·intellij-idea
Herbert_hwt7 小时前
建立Java程序开发
java·开发语言