面向对象编程(OOP)三大特性:封装、继承、多态
封装、继承、多态 —— 这三个词背得滚瓜烂熟,但你真的会用代码讲清楚吗?
👋 你好,我是 Evan,一名计算机专业的学长,也是《大一突围》专栏的作者。记得大一学 Java 时,老师让我们背“OOP 三大特性”,考试也能默写定义,但让我写代码解释什么是多态,我就懵了。今天这篇文章,我不讲枯燥定义,而是直接用Python、Java、C++三种语言的对比示例,帮你彻底搞懂封装、继承、多态到底是什么、怎么用、区别在哪。
欢迎来到《大一突围》专栏。
一、OOP 三大特性一句话概括
二、封装(Encapsulation)
📌 什么是封装?
将数据(属性)和操作数据的方法捆绑在一起,并隐藏内部实现细节,只对外暴露必要的接口(如get/set方法)。就像一台电视机:你只需要按遥控器(接口),不用管内部电路。
📌 封装的好处
安全性:防止外部直接修改内部数据。
模块化:修改内部实现不影响外部调用。
易维护:代码更清晰。
📌 代码示例(Python / Java / C++)
🐍 Python 示例
class Student: def __init__(self, name, age): self.__name = name # 双下划线表示私有属性 self.__age = age def get_name(self): return self.__name def set_age(self, age): if age > 0: self.__age = age else: print("年龄无效") def display(self): print(f"姓名: {self.__name}, 年龄: {self.__age}") # 使用 s = Student("张三", 20) print(s.get_name()) # 通过公有方法访问 s.set_age(21) s.display()☕ Java 示例
public class Student { private String name; private int age; // 构造方法 public Student(String name, int age) { this.name = name; this.age = age; } // 公有 getter/setter public String getName() { return name; } public void setAge(int age) { if (age > 0) { this.age = age; } else { System.out.println("年龄无效"); } } public void display() { System.out.println("姓名: " + name + ", 年龄: " + age); } }⚙️ C++ 示例
#include <iostream> #include <string> using namespace std; class Student { private: string name; int age; public: Student(string n, int a) : name(n), age(a) {} string getName() { return name; } void setAge(int a) { if (a > 0) age = a; else cout << "年龄无效" << endl; } void display() { cout << "姓名: " << name << ", 年龄: " << age << endl; } };小结:封装就是“把成员变量设为私有,通过公有方法访问”。三种语言语法略有不同,但思想完全一致。
三、继承(Inheritance)
📌 什么是继承?
子类(派生类)可以复用父类(基类)的属性和方法,并可以添加自己特有的内容或重写父类方法。
📌 继承的好处
代码复用:避免重复编写相同代码。
层次结构:符合现实世界分类(如:动物 → 猫、狗)。
📌 代码示例
🐍 Python 示例
class Animal: def __init__(self, name): self.name = name def eat(self): print(f"{self.name} 正在吃东西") class Dog(Animal): def bark(self): print(f"{self.name} 在汪汪叫") # 使用 dog = Dog("旺财") dog.eat() # 继承自 Animal dog.bark() # Dog 自己的方法☕ Java 示例
class Animal { String name; Animal(String name) { this.name = name; } void eat() { System.out.println(name + " 正在吃东西"); } } class Dog extends Animal { Dog(String name) { super(name); } void bark() { System.out.println(name + " 在汪汪叫"); } } // 使用 Dog dog = new Dog("旺财"); dog.eat(); dog.bark();⚙️ C++ 示例
class Animal { public: string name; Animal(string n) : name(n) {} void eat() { cout << name << " 正在吃东西" << endl; } }; class Dog : public Animal { public: Dog(string n) : Animal(n) {} void bark() { cout << name << " 在汪汪叫" << endl; } };小结:继承关系用
extends(Java)、: public(C++)或直接括号(Python)表示。子类可调用父类方法,也可扩展自己的方法。
四、多态(Polymorphism)
📌 什么是多态?
同一个方法调用,因为对象类型不同,表现出不同的行为。多态需要三个条件:继承、方法重写、父类引用指向子类对象。
📌 多态的好处
扩展性:新增子类不影响原有代码。
接口统一:父类类型可以接收任意子类对象,调用相同方法产生不同结果。
📌 代码示例
🐍 Python 示例(鸭子类型 + 继承多态)
class Animal: def speak(self): pass class Dog(Animal): def speak(self): print("汪汪") class Cat(Animal): def speak(self): print("喵喵") def make_sound(animal): animal.speak() # 使用 dog = Dog() cat = Cat() make_sound(dog) # 汪汪 make_sound(cat) # 喵喵☕ Java 示例
class Animal { void speak() {} } class Dog extends Animal { void speak() { System.out.println("汪汪"); } } class Cat extends Animal { void speak() { System.out.println("喵喵"); } } // 使用 Animal a1 = new Dog(); Animal a2 = new Cat(); a1.speak(); // 汪汪 a2.speak(); // 喵喵⚙️ C++ 示例(需虚函数)
class Animal { public: virtual void speak() = 0; // 纯虚函数 }; class Dog : public Animal { public: void speak() override { cout << "汪汪" << endl; } }; class Cat : public Animal { public: void speak() override { cout << "喵喵" << endl; } }; // 使用 Animal* a1 = new Dog(); Animal* a2 = new Cat(); a1->speak(); // 汪汪 a2->speak(); // 喵喵注意:C++ 中需要
virtual关键字来实现运行时多态,否则会调用父类版本(静态绑定)。
五、三大特性对比总结表
六、用一句话记住三大特性
封装:我只让你用遥控器,不让你拆电视机。📺
继承:我站在巨人的肩膀上,少写重复代码。🧬
多态:都是“动物”,狗叫“汪汪”,猫叫“喵喵”。🐶🐱
❓ 问题:你在学习 OOP 时,哪个特性最难理解?或者你能否举一个生活中的例子来说明多态?欢迎在评论区分享你的理解或困惑,我会选出 3 位同学,送出《OOP 常见面试题 & 代码案例集》。
📌如果本文帮你搞懂了 OOP 三大特性,请点 👍 赞 + 关注,本专栏《大一突围》持续更新基础编程干货。
收藏本文,遇到 OOP 问题随时回看对比代码。
