🚀 第一阶段:Java基础入门③面向对象编程基础
💡 学习目标:掌握面向对象编程的核心概念,理解类与对象、封装、继承、多态的原理和应用
🏗️ 面向对象编程概述
🎯 什么是面向对象编程?
🌟 面向对象编程(OOP):一种以对象为中心的编程范式,将现实世界的事物抽象为程序中的对象
✨ 面向对象 vs 面向过程
🔄 编程范式对比
│
├── 📝 面向过程编程 (Procedural Programming)
│ ├── 核心:函数/过程
│ ├── 思维:分解问题为步骤
│ ├── 特点:自顶向下,逐步细化
│ └── 示例:C语言
│
└── 🏗️ 面向对象编程 (Object-Oriented Programming)
├── 核心:对象/类
├── 思维:抽象现实世界的事物
├── 特点:封装、继承、多态
└── 示例:Java、C++、Python
🎨 面向对象的四大特性
• 隐藏对象内部实现细节
• 提供公共接口访问
• 保护数据安全性
• 子类继承父类特性
• 代码复用和扩展
• 建立类之间的层次关系
• 同一接口不同实现
• 运行时动态绑定
• 提高代码灵活性
• 提取事物的本质特征
• 忽略不重要的细节
• 简化复杂问题
🌟 面向对象的优势
| 优势 | 说明 | 实际应用 |
|---|---|---|
| 🔄 代码复用 | 通过继承和组合减少重复代码 | 基类定义通用功能 |
| 🛡️ 数据安全 | 封装保护数据不被误用 | 私有属性+公共方法 |
| 🔧 易于维护 | 模块化设计便于修改和扩展 | 修改一个类不影响其他类 |
| 🎯 模块化 | 将复杂系统分解为简单对象 | 每个类负责特定功能 |
| 🤝 团队协作 | 不同开发者可以独立开发不同类 | 接口约定,并行开发 |
📦 类与对象
🎯 类的基本概念
📋 类(Class):对象的模板或蓝图,定义了对象的属性和行为
🏗️ 类的基本结构
// 📋 类的基本结构
[访问修饰符] class 类名 {
// 🔢 属性(成员变量)
[访问修饰符] 数据类型 属性名;
// 🏗️ 构造方法
[访问修饰符] 类名(参数列表) {
// 初始化代码
}
// 📝 方法(成员方法)
[访问修饰符] 返回类型 方法名(参数列表) {
// 方法体
return 返回值; // 如果有返回值
}
}
🎨 实际示例:学生类
/**
* 📚 学生类 - 演示类的基本结构
*/
public class Student {
// 🔢 属性(成员变量) - 描述学生的特征
private String name; // 姓名
private int age; // 年龄
private String studentId; // 学号
private double score; // 成绩
// 🏗️ 无参构造方法
public Student() {
this.name = "未知";
this.age = 0;
this.studentId = "000000";
this.score = 0.0;
}
// 🏗️ 有参构造方法
public Student(String name, int age, String studentId) {
this.name = name;
this.age = age;
this.studentId = studentId;
this.score = 0.0;
}
// 🏗️ 全参构造方法
public Student(String name, int age, String studentId, double score) {
this.name = name;
this.age = age;
this.studentId = studentId;
this.score = score;
}
// 📝 方法(成员方法) - 描述学生的行为
// 📖 学习方法
public void study(String subject) {
System.out.println(name + " 正在学习 " + subject);
}
// 📝 考试方法
public void takeExam(String subject, double score) {
this.score = score;
System.out.println(name + " 参加了 " + subject + " 考试,得分:" + score);
}
// 📊 显示信息方法
public void displayInfo() {
System.out.println("=== 学生信息 ===");
System.out.println("姓名:" + name);
System.out.println("年龄:" + age);
System.out.println("学号:" + studentId);
System.out.println("成绩:" + score);
}
// 🎯 判断是否及格
public boolean isPassed() {
return score >= 60;
}
// 📈 获取等级
public String getGrade() {
if (score >= 90) return "优秀";
else if (score >= 80) return "良好";
else if (score >= 70) return "中等";
else if (score >= 60) return "及格";
else return "不及格";
}
}
🎯 对象的创建和使用
🏗️ 对象(Object):类的实例,具有具体的属性值和可执行的方法
📦 对象的创建语法
public class StudentTest {
public static void main(String[] args) {
// 🏗️ 创建对象的三种方式
// 方式1:使用无参构造方法
Student student1 = new Student();
System.out.println("=== 使用无参构造方法创建对象 ===");
student1.displayInfo();
// 方式2:使用有参构造方法
Student student2 = new Student("张三", 20, "2023001");
System.out.println("\n=== 使用有参构造方法创建对象 ===");
student2.displayInfo();
// 方式3:使用全参构造方法
Student student3 = new Student("李四", 19, "2023002", 85.5);
System.out.println("\n=== 使用全参构造方法创建对象 ===");
student3.displayInfo();
// 📝 调用对象的方法
System.out.println("\n=== 调用对象方法 ===");
student2.study("Java编程");
student2.takeExam("Java编程", 92.0);
// 🎯 使用对象方法获取信息
System.out.println(student2.name + " 是否及格:" + student2.isPassed());
System.out.println(student2.name + " 的等级:" + student2.getGrade());
// 📊 显示更新后的信息
System.out.println("\n=== 更新后的学生信息 ===");
student2.displayInfo();
// 🔄 创建多个对象
Student[] students = {
new Student("王五", 21, "2023003", 78.0),
new Student("赵六", 20, "2023004", 95.5),
new Student("孙七", 19, "2023005", 67.0)
};
System.out.println("\n=== 批量处理学生信息 ===");
for (Student student : students) {
System.out.printf("%s (学号:%s) - 成绩:%.1f - 等级:%s%n",
student.name, student.studentId, student.score, student.getGrade());
}
}
}
🧠 内存中的对象
🧠 Java内存模型中的对象
│
├── 📚 方法区 (Method Area)
│ ├── 类的字节码信息
│ ├── 常量池
│ └── 静态变量
│
├── 🏗️ 堆内存 (Heap)
│ ├── 对象实例数据
│ ├── 实例变量
│ └── 数组元素
│
└── 📋 栈内存 (Stack)
├── 局部变量
├── 方法参数
└── 对象引用
💡 对象创建过程详解
| 步骤 | 操作 | 说明 |
|---|---|---|
| 1️⃣ | 类加载 | JVM加载类的字节码到方法区 |
| 2️⃣ | 内存分配 | 在堆中为对象分配内存空间 |
| 3️⃣ | 初始化 | 设置实例变量的默认值 |
| 4️⃣ | 构造方法 | 执行构造方法中的初始化代码 |
| 5️⃣ | 返回引用 | 返回对象在堆中的内存地址 |
🔧 访问修饰符
🛡️ 访问控制级别
| 修饰符 | 同一类 | 同一包 | 不同包子类 | 不同包非子类 | 使用场景 |
|---|---|---|---|---|---|
public | ✅ | ✅ | ✅ | ✅ | 公共接口 |
protected | ✅ | ✅ | ✅ | ❌ | 继承相关 |
默认(包级私有) | ✅ | ✅ | ❌ | ❌ | 包内使用 |
private | ✅ | ❌ | ❌ | ❌ | 内部实现 |
public class AccessModifierDemo {
// 🔓 public - 公共的,任何地方都可以访问
public String publicField = "公共字段";
// 🔒 protected - 受保护的,同包或子类可以访问
protected String protectedField = "受保护字段";
// 📦 默认(包级私有) - 同包内可以访问
String defaultField = "默认字段";
// 🔐 private - 私有的,只有本类内部可以访问
private String privateField = "私有字段";
// 🔓 公共方法
public void publicMethod() {
System.out.println("这是公共方法");
// 在类内部可以访问所有字段
System.out.println(publicField);
System.out.println(protectedField);
System.out.println(defaultField);
System.out.println(privateField);
}
// 🔐 私有方法
private void privateMethod() {
System.out.println("这是私有方法,只能在类内部调用");
}
// 🎯 演示方法
public void demonstrateAccess() {
privateMethod(); // 类内部可以调用私有方法
}
}
🏗️ 构造方法详解
🎯 构造方法的特点
• 方法名必须与类名完全相同
• 没有返回类型(连void都不写)
• 在创建对象时自动调用
• 可以重载(多个构造方法)
• 如果不定义,系统提供默认无参构造方法
public class Person {
private String name;
private int age;
private String gender;
private String address;
// 🏗️ 无参构造方法
public Person() {
this("未知", 0, "未知", "未知");
System.out.println("调用无参构造方法");
}
// 🏗️ 单参构造方法
public Person(String name) {
this(name, 0, "未知", "未知");
System.out.println("调用单参构造方法");
}
// 🏗️ 双参构造方法
public Person(String name, int age) {
this(name, age, "未知", "未知");
System.out.println("调用双参构造方法");
}
// 🏗️ 三参构造方法
public Person(String name, int age, String gender) {
this(name, age, gender, "未知");
System.out.println("调用三参构造方法");
}
// 🏗️ 全参构造方法
public Person(String name, int age, String gender, String address) {
this.name = name;
this.age = age;
this.gender = gender;
this.address = address;
System.out.println("调用全参构造方法");
}
// 📊 显示信息
public void displayInfo() {
System.out.printf("姓名:%s, 年龄:%d, 性别:%s, 地址:%s%n",
name, age, gender, address);
}
// 🎯 测试构造方法
public static void main(String[] args) {
System.out.println("=== 测试不同构造方法 ===");
Person p1 = new Person();
p1.displayInfo();
Person p2 = new Person("张三");
p2.displayInfo();
Person p3 = new Person("李四", 25);
p3.displayInfo();
Person p4 = new Person("王五", 30, "男");
p4.displayInfo();
Person p5 = new Person("赵六", 28, "女", "合肥市");
p5.displayInfo();
}
}
🔄 this关键字
public class ThisDemo {
private String name;
private int age;
// 🎯 this引用当前对象的属性
public void setName(String name) {
this.name = name; // this.name指向对象属性,name指向参数
}
// 🎯 this调用当前对象的其他方法
public void introduce() {
this.sayHello(); // 可以省略this
System.out.println("我的名字是:" + this.name);
}
private void sayHello() {
System.out.println("大家好!");
}
// 🎯 this调用其他构造方法
public ThisDemo() {
this("默认姓名", 0); // 调用有参构造方法
}
public ThisDemo(String name, int age) {
this.name = name;
this.age = age;
}
// 🎯 this作为返回值(方法链)
public ThisDemo setAge(int age) {
this.age = age;
return this; // 返回当前对象
}
public ThisDemo setNameChain(String name) {
this.name = name;
return this;
}
// 🎯 演示方法链
public static void main(String[] args) {
ThisDemo demo = new ThisDemo();
// 方法链调用
demo.setNameChain("链式调用").setAge(25);
demo.introduce();
}
}
🔒 封装
🎯 封装的概念
🔒 封装(Encapsulation):将对象的属性和方法包装在一起,隐藏内部实现细节,只暴露必要的接口
✨ 封装的核心原则
🔒 封装的实现方式
│
├── 🔐 属性私有化 (private)
│ ├── 防止外部直接访问
│ ├── 保护数据完整性
│ └── 控制访问权限
│
├── 🚪 提供公共接口
│ ├── getter方法 - 获取属性值
│ ├── setter方法 - 设置属性值
│ └── 业务方法 - 执行特定操作
│
└── 🛡️ 数据验证
├── 输入参数检查
├── 业务规则验证
└── 异常处理
🎨 封装的实际应用
/**
* 🏦 银行账户类 - 演示封装的重要性
*/
public class BankAccount {
// 🔐 私有属性 - 外部无法直接访问
private String accountNumber; // 账户号码
private String accountHolder; // 账户持有人
private double balance; // 账户余额
private String password; // 账户密码
private boolean isLocked; // 账户是否被锁定
// 🏗️ 构造方法
public BankAccount(String accountNumber, String accountHolder, String password) {
this.accountNumber = accountNumber;
this.accountHolder = accountHolder;
this.password = password;
this.balance = 0.0;
this.isLocked = false;
}
// 🚪 公共接口 - getter方法
public String getAccountNumber() {
return accountNumber;
}
public String getAccountHolder() {
return accountHolder;
}
public double getBalance() {
return balance;
}
public boolean isLocked() {
return isLocked;
}
// 💰 存款方法
public boolean deposit(double amount) {
if (isLocked) {
System.out.println("❌ 账户已被锁定,无法进行操作!");
return false;
}
if (amount <= 0) {
System.out.println("❌ 存款金额必须大于0!");
return false;
}
balance += amount;
System.out.printf("✅ 存款成功!存入%.2f元,当前余额:%.2f元%n", amount, balance);
return true;
}
// 💸 取款方法
public boolean withdraw(double amount, String password) {
if (isLocked) {
System.out.println("❌ 账户已被锁定,无法进行操作!");
return false;
}
if (!this.password.equals(password)) {
System.out.println("❌ 密码错误!");
return false;
}
if (amount <= 0) {
System.out.println("❌ 取款金额必须大于0!");
return false;
}
if (amount > balance) {
System.out.println("❌ 余额不足!当前余额:" + balance + "元");
return false;
}
balance -= amount;
System.out.printf("✅ 取款成功!取出%.2f元,当前余额:%.2f元%n", amount, balance);
return true;
}
// 📊 显示账户信息
public void displayAccountInfo() {
System.out.println("=== 账户信息 ===");
System.out.println("账户号码:" + accountNumber);
System.out.println("账户持有人:" + accountHolder);
System.out.printf("账户余额:%.2f元%n", balance);
System.out.println("账户状态:" + (isLocked ? "已锁定" : "正常"));
}
}
🎯 JavaBean规范
📋 JavaBean标准
• 类必须是public的
• 必须有无参构造方法
• 属性必须是private的
• 提供public的getter和setter方法
• getter方法以get开头,setter方法以set开头
• boolean类型的getter可以以is开头
/**
* 📱 手机类 - 标准JavaBean示例
*/
public class Phone {
// 🔐 私有属性
private String brand; // 品牌
private String model; // 型号
private double price; // 价格
private int storage; // 存储容量(GB)
private boolean isSmartPhone; // 是否为智能手机
// 🏗️ 无参构造方法(必须)
public Phone() {
}
// 🚪 Getter方法
public String getBrand() {
return brand;
}
public double getPrice() {
return price;
}
// 🎯 boolean类型的getter可以用is开头
public boolean isSmartPhone() {
return isSmartPhone;
}
// 🚪 Setter方法
public void setBrand(String brand) {
this.brand = brand;
}
public void setPrice(double price) {
if (price >= 0) {
this.price = price;
} else {
System.out.println("❌ 价格不能为负数!");
}
}
public void setSmartPhone(boolean smartPhone) {
this.isSmartPhone = smartPhone;
}
// 📊 toString方法(推荐重写)
@Override
public String toString() {
return String.format("Phone{品牌='%s', 型号='%s', 价格=%.2f, 存储=%dGB, 智能手机=%s}",
brand, model, price, storage, isSmartPhone ? "是" : "否");
}
}
🧬 继承
🎯 继承的概念
🧬 继承(Inheritance):子类继承父类的属性和方法,实现代码复用和扩展
✨ 继承的核心特点
🧬 Java继承体系
│
├── 🏗️ 父类 (Super Class / Base Class)
│ ├── 定义通用属性和方法
│ ├── 被子类继承
│ └── 也称为基类或超类
│
├── 👶 子类 (Sub Class / Derived Class)
│ ├── 继承父类的特性
│ ├── 可以添加新的属性和方法
│ ├── 可以重写父类的方法
│ └── 也称为派生类
│
└── 🔗 继承关系
├── 使用extends关键字
├── Java只支持单继承
└── 形成类的层次结构
🎨 继承的实际应用
/**
* 🐾 动物基类 - 父类
*/
public class Animal {
// 🔒 受保护的属性 - 子类可以访问
protected String name;
protected int age;
protected String species;
// 🏗️ 构造方法
public Animal() {
this.name = "未知";
this.age = 0;
this.species = "未知";
}
public Animal(String name, int age, String species) {
this.name = name;
this.age = age;
this.species = species;
}
// 🍽️ 吃的方法
public void eat() {
System.out.println(name + " 正在吃东西");
}
// 😴 睡觉的方法
public void sleep() {
System.out.println(name + " 正在睡觉");
}
// 🏃 移动的方法
public void move() {
System.out.println(name + " 正在移动");
}
// 📊 显示信息
public void displayInfo() {
System.out.println("=== 动物信息 ===");
System.out.println("名字:" + name);
System.out.println("年龄:" + age);
System.out.println("种类:" + species);
}
// 🎵 发出声音的方法(将被子类重写)
public void makeSound() {
System.out.println(name + " 发出了声音");
}
}
/**
* 🐕 狗类 - 继承自Animal
*/
public class Dog extends Animal {
// 🆕 子类特有的属性
private String breed; // 品种
private boolean isTrained; // 是否训练过
// 🏗️ 构造方法
public Dog() {
super(); // 调用父类无参构造方法
this.breed = "未知品种";
this.isTrained = false;
}
public Dog(String name, int age, String breed) {
super(name, age, "犬类"); // 调用父类有参构造方法
this.breed = breed;
this.isTrained = false;
}
public Dog(String name, int age, String breed, boolean isTrained) {
super(name, age, "犬类");
this.breed = breed;
this.isTrained = isTrained;
}
// 🎵 重写父类的makeSound方法
@Override
public void makeSound() {
System.out.println(name + " 汪汪叫");
}
// 🏃 重写父类的move方法
@Override
public void move() {
System.out.println(name + " 正在奔跑");
}
// 🆕 子类特有的方法
public void wagTail() {
System.out.println(name + " 摇尾巴表示友好");
}
public void fetch() {
if (isTrained) {
System.out.println(name + " 去捡球");
} else {
System.out.println(name + " 还没学会捡球");
}
}
public void guard() {
System.out.println(name + " 正在看家护院");
}
// 📊 重写显示信息方法
@Override
public void displayInfo() {
super.displayInfo(); // 调用父类的方法
System.out.println("品种:" + breed);
System.out.println("是否训练过:" + (isTrained ? "是" : "否"));
}
// Getter和Setter方法
public String getBreed() {
return breed;
}
public void setBreed(String breed) {
this.breed = breed;
}
public boolean isTrained() {
return isTrained;
}
public void setTrained(boolean trained) {
this.isTrained = trained;
}
}
/**
* 🐱 猫类 - 继承自Animal
*/
public class Cat extends Animal {
// 🆕 子类特有的属性
private String furColor; // 毛色
private boolean isIndoor; // 是否室内猫
// 🏗️ 构造方法
public Cat(String name, int age, String furColor) {
super(name, age, "猫科");
this.furColor = furColor;
this.isIndoor = true;
}
// 🎵 重写父类的makeSound方法
@Override
public void makeSound() {
System.out.println(name + " 喵喵叫");
}
// 🏃 重写父类的move方法
@Override
public void move() {
System.out.println(name + " 优雅地走动");
}
// 🆕 子类特有的方法
public void purr() {
System.out.println(name + " 发出呼噜声表示满足");
}
public void climb() {
System.out.println(name + " 爬到高处");
}
public void hunt() {
if (!isIndoor) {
System.out.println(name + " 正在捕猎");
} else {
System.out.println(name + " 在室内玩玩具老鼠");
}
}
// 📊 重写显示信息方法
@Override
public void displayInfo() {
super.displayInfo();
System.out.println("毛色:" + furColor);
System.out.println("生活环境:" + (isIndoor ? "室内" : "室外"));
}
}
🧪 继承测试示例
public class InheritanceTest {
public static void main(String[] args) {
System.out.println("=== 测试继承特性 ===");
// 🐾 创建动物对象
Animal animal = new Animal("通用动物", 5, "未知");
animal.displayInfo();
animal.eat();
animal.makeSound();
System.out.println("\n" + "=".repeat(30));
// 🐕 创建狗对象
Dog dog = new Dog("旺财", 3, "金毛");
dog.displayInfo();
dog.eat(); // 继承自父类
dog.makeSound(); // 重写的方法
dog.move(); // 重写的方法
dog.wagTail(); // 子类特有方法
dog.fetch(); // 子类特有方法
dog.guard(); // 子类特有方法
System.out.println("\n" + "=".repeat(30));
// 🐱 创建猫对象
Cat cat = new Cat("咪咪", 2, "橘色");
cat.displayInfo();
cat.eat(); // 继承自父类
cat.makeSound(); // 重写的方法
cat.move(); // 重写的方法
cat.purr(); // 子类特有方法
cat.climb(); // 子类特有方法
cat.hunt(); // 子类特有方法
System.out.println("\n=== 多态性演示 ===");
// 🎭 多态:父类引用指向子类对象
Animal[] animals = {
new Animal("普通动物", 1, "未知"),
new Dog("小黑", 4, "拉布拉多"),
new Cat("小白", 3, "白色")
};
for (Animal a : animals) {
System.out.println("\n--- " + a.name + " ---");
a.makeSound(); // 调用各自重写的方法
a.move(); // 调用各自重写的方法
}
}
}
🔑 super关键字
🎯 super的作用
• 调用父类的构造方法:super()
• 访问父类的属性:super.属性名
• 调用父类的方法:super.方法名()
• 在子类中区分父类和子类的同名成员
public class Vehicle {
protected String brand;
protected int maxSpeed;
public Vehicle(String brand, int maxSpeed) {
this.brand = brand;
this.maxSpeed = maxSpeed;
}
public void start() {
System.out.println(brand + " 启动了");
}
public void displayInfo() {
System.out.println("品牌:" + brand + ",最高速度:" + maxSpeed + "km/h");
}
}
public class Car extends Vehicle {
private int doors;
private String fuelType;
public Car(String brand, int maxSpeed, int doors, String fuelType) {
super(brand, maxSpeed); // 调用父类构造方法
this.doors = doors;
this.fuelType = fuelType;
}
@Override
public void start() {
super.start(); // 调用父类的start方法
System.out.println("汽车准备就绪,可以行驶");
}
@Override
public void displayInfo() {
super.displayInfo(); // 调用父类的displayInfo方法
System.out.println("车门数:" + doors + ",燃料类型:" + fuelType);
}
}
🎭 多态
🎯 多态的概念
🎭 多态(Polymorphism):同一个接口,不同的实现;同一个方法调用,不同的执行结果
✨ 多态的实现条件
🎭 多态的三个必要条件
│
├── 🧬 继承关系
│ └── 子类继承父类或实现接口
│
├── 🔄 方法重写
│ └── 子类重写父类的方法
│
└── 🎯 向上转型
└── 父类引用指向子类对象
🎨 多态的实际应用
/**
* 🔷 图形基类
*/
public abstract class Shape {
protected String color;
public Shape(String color) {
this.color = color;
}
// 🎯 抽象方法 - 子类必须实现
public abstract double calculateArea();
public abstract double calculatePerimeter();
// 🎨 具体方法
public void displayColor() {
System.out.println("颜色:" + color);
}
public void displayInfo() {
System.out.println("=== 图形信息 ===");
displayColor();
System.out.printf("面积:%.2f%n", calculateArea());
System.out.printf("周长:%.2f%n", calculatePerimeter());
}
}
/**
* ⭕ 圆形类
*/
public class Circle extends Shape {
private double radius;
public Circle(String color, double radius) {
super(color);
this.radius = radius;
}
@Override
public double calculateArea() {
return Math.PI * radius * radius;
}
@Override
public double calculatePerimeter() {
return 2 * Math.PI * radius;
}
@Override
public void displayInfo() {
System.out.println("=== 圆形信息 ===");
super.displayColor();
System.out.println("半径:" + radius);
System.out.printf("面积:%.2f%n", calculateArea());
System.out.printf("周长:%.2f%n", calculatePerimeter());
}
}
/**
* ⬜ 矩形类
*/
public class Rectangle extends Shape {
private double width;
private double height;
public Rectangle(String color, double width, double height) {
super(color);
this.width = width;
this.height = height;
}
@Override
public double calculateArea() {
return width * height;
}
@Override
public double calculatePerimeter() {
return 2 * (width + height);
}
@Override
public void displayInfo() {
System.out.println("=== 矩形信息 ===");
super.displayColor();
System.out.println("宽度:" + width + ",高度:" + height);
System.out.printf("面积:%.2f%n", calculateArea());
System.out.printf("周长:%.2f%n", calculatePerimeter());
}
}
/**
* 🔺 三角形类
*/
public class Triangle extends Shape {
private double side1, side2, side3;
public Triangle(String color, double side1, double side2, double side3) {
super(color);
this.side1 = side1;
this.side2 = side2;
this.side3 = side3;
}
@Override
public double calculateArea() {
// 使用海伦公式计算面积
double s = (side1 + side2 + side3) / 2;
return Math.sqrt(s * (s - side1) * (s - side2) * (s - side3));
}
@Override
public double calculatePerimeter() {
return side1 + side2 + side3;
}
@Override
public void displayInfo() {
System.out.println("=== 三角形信息 ===");
super.displayColor();
System.out.printf("三边长:%.1f, %.1f, %.1f%n", side1, side2, side3);
System.out.printf("面积:%.2f%n", calculateArea());
System.out.printf("周长:%.2f%n", calculatePerimeter());
}
}
🧪 多态测试示例
public class PolymorphismTest {
public static void main(String[] args) {
System.out.println("=== 多态性演示 ===");
// 🎭 多态:父类引用指向不同的子类对象
Shape[] shapes = {
new Circle("红色", 5.0),
new Rectangle("蓝色", 4.0, 6.0),
new Triangle("绿色", 3.0, 4.0, 5.0)
};
// 🔄 统一处理不同类型的图形
double totalArea = 0;
for (Shape shape : shapes) {
shape.displayInfo(); // 调用各自重写的方法
totalArea += shape.calculateArea();
System.out.println();
}
System.out.printf("所有图形的总面积:%.2f%n", totalArea);
// 🎯 演示多态的动态绑定
System.out.println("\n=== 动态绑定演示 ===");
processShape(new Circle("黄色", 3.0));
processShape(new Rectangle("紫色", 5.0, 8.0));
processShape(new Triangle("橙色", 6.0, 8.0, 10.0));
}
// 🎭 多态方法:接受任何Shape类型的对象
public static void processShape(Shape shape) {
System.out.println("正在处理图形...");
shape.displayInfo();
// 🔍 类型判断和向下转型
if (shape instanceof Circle) {
Circle circle = (Circle) shape;
System.out.println("这是一个圆形");
} else if (shape instanceof Rectangle) {
Rectangle rectangle = (Rectangle) shape;
System.out.println("这是一个矩形");
} else if (shape instanceof Triangle) {
Triangle triangle = (Triangle) shape;
System.out.println("这是一个三角形");
}
System.out.println();
}
}
🔄 类型转换
🔼 向上转型(自动)
• 子类对象赋值给父类引用
• 自动进行,无需强制转换
• 安全的类型转换
• 只能访问父类中定义的方法
🔽 向下转型(强制)
• 父类引用转换为子类引用
• 需要强制类型转换
• 可能抛出ClassCastException
• 建议使用instanceof检查类型
🎯 抽象类与接口
🎯 抽象类
🎯 抽象类(Abstract Class):不能被实例化的类,通常包含抽象方法,用于定义子类的通用结构
✨ 抽象类的特点
• 使用abstract关键字修饰
• 不能被实例化(不能new)
• 可以包含抽象方法和具体方法
• 可以有构造方法、属性、静态方法
• 子类必须实现所有抽象方法(除非子类也是抽象类)
/**
* 🎵 音乐播放器抽象类
*/
public abstract class MusicPlayer {
protected String brand;
protected double volume;
protected boolean isPlaying;
// 🏗️ 构造方法
public MusicPlayer(String brand) {
this.brand = brand;
this.volume = 50.0;
this.isPlaying = false;
}
// 🎯 抽象方法 - 子类必须实现
public abstract void play(String song);
public abstract void pause();
public abstract void stop();
public abstract void next();
public abstract void previous();
// 🎵 具体方法 - 子类可以直接使用
public void setVolume(double volume) {
if (volume >= 0 && volume <= 100) {
this.volume = volume;
System.out.println("音量设置为:" + volume);
} else {
System.out.println("音量范围应在0-100之间");
}
}
public void displayInfo() {
System.out.println("=== 播放器信息 ===");
System.out.println("品牌:" + brand);
System.out.println("音量:" + volume);
System.out.println("播放状态:" + (isPlaying ? "播放中" : "已停止"));
}
// 🔧 静态方法
public static void showSupportedFormats() {
System.out.println("支持的音频格式:MP3, WAV, FLAC");
}
}
/**
* 📱 手机音乐播放器
*/
public class PhoneMusicPlayer extends MusicPlayer {
private String[] playlist;
private int currentIndex;
public PhoneMusicPlayer(String brand, String[] playlist) {
super(brand);
this.playlist = playlist;
this.currentIndex = 0;
}
@Override
public void play(String song) {
isPlaying = true;
System.out.println("📱 手机播放器正在播放:" + song);
}
@Override
public void pause() {
isPlaying = false;
System.out.println("⏸️ 暂停播放");
}
@Override
public void stop() {
isPlaying = false;
currentIndex = 0;
System.out.println("⏹️ 停止播放");
}
@Override
public void next() {
if (currentIndex < playlist.length - 1) {
currentIndex++;
play(playlist[currentIndex]);
} else {
System.out.println("已经是最后一首歌了");
}
}
@Override
public void previous() {
if (currentIndex > 0) {
currentIndex--;
play(playlist[currentIndex]);
} else {
System.out.println("已经是第一首歌了");
}
}
}
🔗 接口
🔗 接口(Interface):定义类应该具有的行为规范,是一种完全抽象的"类"
✨ 接口的特点
• 使用interface关键字定义
• 所有方法默认是public abstract的
• 所有属性默认是public static final的
• 不能有构造方法
• 类可以实现多个接口
• 接口可以继承其他接口
/**
* 🏊 游泳接口
*/
public interface Swimmable {
// 🌊 常量(默认public static final)
double WATER_DENSITY = 1000.0;
// 🏊 抽象方法(默认public abstract)
void swim();
void dive();
double getSwimSpeed();
}
/**
* 🕊️ 飞行接口
*/
public interface Flyable {
// ☁️ 常量
double AIR_DENSITY = 1.225;
// 🕊️ 抽象方法
void fly();
void land();
double getFlyHeight();
// 🎯 默认方法(Java 8+)
default void takeOff() {
System.out.println("准备起飞...");
fly();
}
}
/**
* 🏃 跑步接口
*/
public interface Runnable {
void run();
double getRunSpeed();
// 🔧 静态方法(Java 8+)
static void showRunningTips() {
System.out.println("跑步小贴士:保持匀速,注意呼吸");
}
}
/**
* 🦆 鸭子类 - 实现多个接口
*/
public class Duck implements Swimmable, Flyable, Runnable {
private String name;
private double swimSpeed;
private double flyHeight;
private double runSpeed;
public Duck(String name) {
this.name = name;
this.swimSpeed = 5.0;
this.flyHeight = 100.0;
this.runSpeed = 8.0;
}
// 🏊 实现Swimmable接口
@Override
public void swim() {
System.out.println(name + " 在水中游泳");
}
@Override
public void dive() {
System.out.println(name + " 潜入水中觅食");
}
@Override
public double getSwimSpeed() {
return swimSpeed;
}
// 🕊️ 实现Flyable接口
@Override
public void fly() {
System.out.println(name + " 在天空中飞翔");
}
@Override
public void land() {
System.out.println(name + " 降落到地面");
}
@Override
public double getFlyHeight() {
return flyHeight;
}
// 🏃 实现Runnable接口
@Override
public void run() {
System.out.println(name + " 在地面上奔跑");
}
@Override
public double getRunSpeed() {
return runSpeed;
}
// 🎯 鸭子特有的方法
public void quack() {
System.out.println(name + " 嘎嘎叫");
}
public void displayAbilities() {
System.out.println("=== " + name + " 的能力 ===");
System.out.println("游泳速度:" + swimSpeed + " km/h");
System.out.println("飞行高度:" + flyHeight + " m");
System.out.println("奔跑速度:" + runSpeed + " km/h");
}
}
🆚 抽象类 vs 接口
| 特性 | 抽象类 | 接口 |
|---|---|---|
| 🔑 关键字 | abstract class | interface |
| 🏗️ 构造方法 | ✅ 可以有 | ❌ 不能有 |
| 📦 属性 | 可以有各种类型的属性 | 只能有常量(public static final) |
| 📝 方法 | 可以有抽象和具体方法 | 主要是抽象方法,可以有默认和静态方法 |
| 🧬 继承 | 单继承(extends) | 多实现(implements) |
| 🎯 实例化 | ❌ 不能直接实例化 | ❌ 不能直接实例化 |
| 🔒 访问修饰符 | 可以有各种访问修饰符 | 方法默认public,属性默认public static final |
| 🎨 使用场景 | 有共同实现的相关类 | 定义行为规范,不相关的类 |
🤔 常见问题与解决方案
❓ 面向对象设计常见问题
1️⃣ 什么时候使用继承,什么时候使用组合?
过度使用继承,导致类层次过深,代码难以维护
使用继承的场景:
• 存在明确的"is-a"关系(狗是动物)
• 需要利用多态性
• 子类是父类的特殊化
使用组合的场景:
• 存在"has-a"关系(汽车有引擎)
• 需要在运行时改变行为
• 避免继承层次过深
// ❌ 错误的继承使用
class Rectangle {
protected int width, height;
public void setWidth(int width) { this.width = width; }
public void setHeight(int height) { this.height = height; }
}
class Square extends Rectangle {
// 违反了里氏替换原则
@Override
public void setWidth(int width) {
this.width = this.height = width;
}
}
// ✅ 正确的组合使用
class Car {
private Engine engine; // 组合关系
private Wheel[] wheels; // 组合关系
public Car() {
this.engine = new Engine();
this.wheels = new Wheel[4];
}
public void start() {
engine.start(); // 委托给组合对象
}
}
class Engine {
public void start() {
System.out.println("引擎启动");
}
}
2️⃣ 抽象类和接口如何选择?
| 选择标准 | 抽象类 | 接口 |
|---|---|---|
| 🎯 关系类型 | 强"is-a"关系 | "can-do"能力 |
| 🔄 代码复用 | 需要共享代码实现 | 只需要方法签名 |
| 🧬 继承数量 | 单继承限制 | 可以实现多个 |
| 🔧 未来扩展 | 可以添加具体方法 | 添加方法会破坏兼容性 |
| 📦 状态管理 | 需要维护状态 | 无状态或常量 |
• 如果多个类有共同的代码实现,使用抽象类
• 如果只是定义行为规范,使用接口
• 如果需要多重继承的效果,使用接口
• 如果类之间关系紧密,使用抽象类
3️⃣ 如何避免方法重写的常见错误?
class Parent {
public void display(String msg) {
System.out.println("Parent: " + msg);
}
public static void staticMethod() {
System.out.println("Parent static");
}
private void privateMethod() {
System.out.println("Parent private");
}
}
class Child extends Parent {
// ❌ 错误1:参数不同,这是重载不是重写
public void display(int num) {
System.out.println("Child: " + num);
}
// ❌ 错误2:试图重写静态方法(实际是隐藏)
public static void staticMethod() {
System.out.println("Child static");
}
// ❌ 错误3:试图重写私有方法(实际是新方法)
public void privateMethod() {
System.out.println("Child private");
}
// ✅ 正确的重写
@Override
public void display(String msg) {
System.out.println("Child: " + msg);
}
}
• 使用@Override注解确保正确重写
• 子类方法的访问权限不能比父类更严格
• 静态方法不能被重写,只能被隐藏
• 私有方法不能被重写
• 构造方法不能被重写
4️⃣ 如何正确使用多态?
// ✅ 正确的多态使用
public class ShapeProcessor {
// 面向接口编程
public double calculateTotalArea(List<Shape> shapes) {
double total = 0;
for (Shape shape : shapes) {
total += shape.calculateArea(); // 多态调用
}
return total;
}
// 使用多态避免if-else链
public void processShape(Shape shape) {
shape.displayInfo(); // 每个子类有不同的实现
// 必要时进行类型检查
if (shape instanceof Circle) {
Circle circle = (Circle) shape;
// 处理圆形特有的逻辑
}
}
}
// ❌ 避免的反模式
public class BadShapeProcessor {
public void processShape(Object shape) {
// 避免使用instanceof链
if (shape instanceof Circle) {
Circle circle = (Circle) shape;
// 处理圆形
} else if (shape instanceof Rectangle) {
Rectangle rect = (Rectangle) shape;
// 处理矩形
} else if (shape instanceof Triangle) {
Triangle tri = (Triangle) shape;
// 处理三角形
}
// 这种方式违反了开闭原则
}
}
🎨 面向对象设计思路
🎯 设计原则与思维模式
🎨 面向对象设计思维流程
│
├── 1️⃣ 需求分析
│ ├── 识别系统中的实体
│ ├── 分析实体之间的关系
│ └── 确定系统的主要功能
│
├── 2️⃣ 概念建模
│ ├── 抽象出核心概念
│ ├── 定义类的职责
│ └── 设计类的接口
│
├── 3️⃣ 关系设计
│ ├── 确定继承关系
│ ├── 定义组合关系
│ └── 设计接口契约
│
├── 4️⃣ 实现细节
│ ├── 选择合适的数据结构
│ ├── 实现算法逻辑
│ └── 处理异常情况
│
└── 5️⃣ 重构优化
├── 消除代码重复
├── 提高代码可读性
└── 优化性能瓶颈
🏗️ 实际设计案例:图书管理系统
// 1️⃣ 需求分析:图书管理系统需要管理图书、用户、借阅记录
// 2️⃣ 概念建模:抽象出核心实体
/**
* 📚 图书基类 - 封装图书的基本信息
*/
public abstract class Book {
protected String isbn;
protected String title;
protected String author;
protected double price;
protected boolean isAvailable;
// 构造方法、getter/setter省略...
// 抽象方法:不同类型的书有不同的借阅规则
public abstract int getMaxBorrowDays();
public abstract double getLateFee();
}
// 3️⃣ 关系设计:继承关系
/**
* 📖 普通图书
*/
public class RegularBook extends Book {
@Override
public int getMaxBorrowDays() {
return 30; // 普通图书可借30天
}
@Override
public double getLateFee() {
return 0.5; // 每天0.5元滞纳金
}
}
/**
* 📚 参考书籍
*/
public class ReferenceBook extends Book {
@Override
public int getMaxBorrowDays() {
return 7; // 参考书只能借7天
}
@Override
public double getLateFee() {
return 1.0; // 每天1元滞纳金
}
}
// 4️⃣ 接口设计:定义行为契约
/**
* 🔍 可搜索接口
*/
public interface Searchable {
boolean matchesKeyword(String keyword);
}
/**
* 📊 可统计接口
*/
public interface Countable {
int getBorrowCount();
void incrementBorrowCount();
}
// 5️⃣ 组合关系:用户和借阅记录
/**
* 👤 用户类
*/
public class User {
private String userId;
private String name;
private List<BorrowRecord> borrowHistory; // 组合关系
public boolean canBorrow() {
// 检查用户是否可以借书
return borrowHistory.stream()
.mapToInt(record -> record.isOverdue() ? 1 : 0)
.sum() < 3; // 最多3本逾期书
}
}
/**
* 📋 借阅记录类
*/
public class BorrowRecord {
private User user;
private Book book;
private LocalDate borrowDate;
private LocalDate dueDate;
private LocalDate returnDate;
public boolean isOverdue() {
return returnDate == null && LocalDate.now().isAfter(dueDate);
}
public double calculateLateFee() {
if (!isOverdue()) return 0;
long overdueDays = ChronoUnit.DAYS.between(dueDate, LocalDate.now());
return overdueDays * book.getLateFee(); // 多态调用
}
}
/**
* 📚 图书管理系统主类
*/
public class LibrarySystem {
private List<Book> books;
private List<User> users;
private List<BorrowRecord> records;
// 使用多态处理不同类型的图书
public void addBook(Book book) {
books.add(book);
System.out.println("添加图书:" + book.getTitle() +
",最大借阅天数:" + book.getMaxBorrowDays());
}
// 面向接口编程
public List<Book> searchBooks(String keyword) {
return books.stream()
.filter(book -> book instanceof Searchable)
.filter(book -> ((Searchable) book).matchesKeyword(keyword))
.collect(Collectors.toList());
}
}
🔧 设计模式预览
• 单例模式:确保类只有一个实例(如数据库连接)
• 工厂模式:创建对象的统一接口(如创建不同类型的图书)
• 观察者模式:对象间的一对多依赖关系(如图书状态变化通知)
• 策略模式:算法的封装和互换(如不同的借阅规则)
• 装饰器模式:动态添加对象功能(如图书的特殊标记)
💡 设计经验总结
🎨 好的设计特征
| 特征 | 说明 | 实现方式 |
|---|---|---|
| 🎯 高内聚 | 类内部元素紧密相关 | 单一职责原则 |
| 🔗 低耦合 | 类之间依赖关系最小 | 依赖注入、接口编程 |
| 🔄 可扩展 | 易于添加新功能 | 开闭原则、多态性 |
| 🔧 可维护 | 易于修改和调试 | 清晰的命名、适当的注释 |
| 🧪 可测试 | 易于编写单元测试 | 依赖注入、接口抽象 |
🚫 应该避免的设计
• 上帝类:一个类承担过多职责
• 贫血模型:类只有数据没有行为
• 意大利面条代码:类之间关系混乱
• 硬编码:将配置信息写死在代码中
• 过度设计:为了设计而设计,增加不必要的复杂性
🎯 设计检查清单
• 每个类是否只有一个变化的理由?
• 类之间的依赖关系是否清晰?
• 是否可以轻松添加新的功能?
• 代码是否易于理解和维护?
• 是否遵循了命名约定?
• 是否有适当的错误处理?
📝 本章小结
🎉 恭喜!你已经掌握了面向对象编程的核心概念!
✅ 学习成果检查清单
🎯 知识掌握情况
| 学习内容 | 掌握程度 | 检查方式 |
|---|---|---|
| 🏗️ 类与对象 | ✅ 已掌握 | 能创建类并实例化对象 |
| 🔒 封装 | ✅ 已掌握 | 理解private属性和public方法 |
| 🧬 继承 | ✅ 已掌握 | 能使用extends创建子类 |
| 🎭 多态 | ✅ 已掌握 | 理解方法重写和动态绑定 |
| 🎯 抽象类 | ✅ 已掌握 | 能定义和使用抽象类 |
| 🔗 接口 | ✅ 已掌握 | 能定义接口并实现多个接口 |
🏆 技能成就解锁
掌握类的设计和对象创建
理解数据隐藏和接口设计
熟练使用继承实现代码复用
掌握多态性和动态绑定
🎯 核心概念总结
📊 面向对象四大特性
| 特性 | 核心概念 | 实现方式 | 主要作用 |
|---|---|---|---|
| 🔒 封装 | 数据隐藏 | private属性 + public方法 | 保护数据,控制访问 |
| 🧬 继承 | 代码复用 | extends关键字 | 建立类层次,复用代码 |
| 🎭 多态 | 一个接口多种实现 | 方法重写 + 向上转型 | 提高灵活性,统一处理 |
| 🎯 抽象 | 提取本质特征 | 抽象类 + 接口 | 定义规范,隐藏细节 |
🔑 关键字速查表
| 关键字 | 用途 | 示例 |
|---|---|---|
class | 定义类 | public class Student {} |
extends | 继承类 | class Dog extends Animal |
implements | 实现接口 | class Duck implements Flyable |
abstract | 抽象类/方法 | abstract class Shape |
interface | 定义接口 | interface Runnable |
super | 调用父类 | super.method() |
this | 引用当前对象 | this.name = name |
instanceof | 类型检查 | obj instanceof String |
@Override | 方法重写注解 | @Override public void run() |
📋 实战练习作业
💪 实践出真知:通过练习巩固面向对象编程技能
🎯 基础练习(必做)
练习1:学生管理系统 ⭐⭐⭐
// 设计Person基类,Student和Teacher子类
// 实现封装:私有属性,公共方法
// 实现继承:子类继承父类特性
// 实现多态:统一处理不同类型的人员
练习2:图形计算器 ⭐⭐⭐⭐
// 设计Shape抽象类
// 实现Circle、Rectangle、Triangle子类
// 使用多态计算不同图形的面积和周长
// 实现Drawable接口,添加绘制功能
🚀 进阶练习(选做)
练习3:动物园管理系统 ⭐⭐⭐⭐⭐
// 设计Animal抽象类和多个接口
// 实现多种动物类(哺乳动物、鸟类、鱼类等)
// 使用多态和接口实现复杂的行为组合
// 添加饲养员类和管理功能
练习4:媒体播放器 ⭐⭐⭐⭐⭐
// 设计MediaPlayer抽象类
// 实现AudioPlayer、VideoPlayer子类
// 定义Playable、Controllable接口
// 实现播放列表和控制功能
🔍 设计原则与最佳实践
🎯 SOLID原则简介
| 原则 | 英文 | 中文 | 核心思想 |
|---|---|---|---|
| S | Single Responsibility | 单一职责 | 一个类只负责一个功能 |
| O | Open/Closed | 开闭原则 | 对扩展开放,对修改关闭 |
| L | Liskov Substitution | 里氏替换 | 子类可以替换父类 |
| I | Interface Segregation | 接口隔离 | 接口应该小而专一 |
| D | Dependency Inversion | 依赖倒置 | 依赖抽象而非具体实现 |
💡 编程最佳实践
• 优先使用组合而非继承
• 面向接口编程,而非面向实现
• 保持类的单一职责
• 合理使用访问修饰符
• 重写equals()和hashCode()方法
• 提供有意义的toString()方法
🗺️ 专栏学习路径图
📈 Java程序员从0到1成长路径
🎯 第一阶段:Java基础入门 (4-6周)
┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ 1.开发环境 │───▶│ 2.基础语法 │───▶│ 3.面向对象 │───▶│ 4.核心API │
│ 搭建 │ │ │ │ 编程基础 │ │ │
│ ✅ 已完成 │ │ ✅ 已完成 │ │ ✅ 已完成 │ │ 🎯 下一步 │
└─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘
🚀 第二阶段:Java进阶技能 (4-6周)
┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ 1.高级特性 │ │ 2.I/O与网络 │ │ 3.新特性 │ │ 4.工具框架 │
│ │ │ 编程 │ │ │ │ 入门 │
│ 📅 计划中 │ │ 📅 计划中 │ │ 📅 计划中 │ │ 📅 计划中 │
└─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘
🎯 第三阶段:项目实战 (4-8周)
┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ 1.小型项目 │ │ 2.Web开发 │ │ 3.Spring │ │ 4.数据库与 │
│ 开发 │ │ 基础 │ │ 框架入门 │ │ 持久层 │
│ 📅 计划中 │ │ 📅 计划中 │ │ 📅 计划中 │ │ 📅 计划中 │
└─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘
🏆 第四阶段:职业发展 (持续更新)
┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ 1.代码质量 │ │ 2.开发工具 │ │ 3.面试准备 │ │ 4.职业规划 │
│ 与规范 │ │ 链 │ │ │ │ │
│ 📅 计划中 │ │ 📅 计划中 │ │ 📅 计划中 │ │ 📅 计划中 │
└─────────────┘ └─────────────┘ └─────────────┘ └─────────────┘
📋 第一阶段学习进度
| 章节 | 主要内容 | 预计时间 | 难度 | 状态 |
|---|---|---|---|---|
| 📚 1.开发环境搭建 | JDK安装、Hello World、IDE使用 | 1-2天 | ⭐⭐ | ✅ 已完成 |
| 📝 2.基础语法 | 变量、数据类型、运算符、流程控制 | 1周 | ⭐⭐⭐ | ✅ 已完成 |
| 🏗️ 3.面向对象基础 | 类与对象、封装、继承、多态 | 1-2周 | ⭐⭐⭐⭐ | ✅ 已完成 |
| 🔧 4.核心API | String、集合框架、异常处理 | 1周 | ⭐⭐⭐ | 🎯 下一步 |
• 第一阶段进度:75% (3/4章节完成)
• 下一步:学习Java核心API
• 建议:巩固面向对象概念,准备学习常用API
• 重点:掌握String类、集合框架和异常处理机制
📚 推荐学习资源
🌟 经典书籍
| 书籍 | 作者 | 难度 | 推荐指数 |
|---|---|---|---|
| 📖 《Head First设计模式》 | Freeman等 | ⭐⭐⭐ | ⭐⭐⭐⭐⭐ |
| 📖 《Effective Java》 | Joshua Bloch | ⭐⭐⭐⭐ | ⭐⭐⭐⭐⭐ |
| 📖 《Java编程思想》 | Bruce Eckel | ⭐⭐⭐⭐ | ⭐⭐⭐⭐ |
| 📖 《重构:改善既有代码的设计》 | Martin Fowler | ⭐⭐⭐⭐ | ⭐⭐⭐⭐ |
🎥 在线资源
• 慕课网Java面向对象课程 - 系统学习OOP概念
• B站尚硅谷Java教程 - 深入理解面向对象
• 极客时间Java核心技术 - 专业级别的讲解
• Oracle官方Java教程 - 权威的学习资料
🎬 下一章预告
📦 第一阶段第4章:Java核心API
🎯 下章学习内容
- 📝 String和常用类的使用
- 📊 集合框架(List、Set、Map)
- 🚨 异常处理机制与最佳实践
- 🔢 包装类与自动装箱拆箱
- 📅 日期时间API的应用
📚 学习重点
- 掌握String类和常用工具类
- 熟练使用Java集合框架
- 理解异常处理的原理和应用
- 学会选择合适的数据结构
- 提高程序的健壮性和可维护性
💡 学习小贴士
面向对象编程是Java的核心!
掌握了OOP思想,你就掌握了Java编程的精髓!
记住:好的设计胜过复杂的实现! 🌟
📧 有问题?欢迎在评论区讨论交流!
⭐ 觉得有用?别忘了点赞收藏!
🔄 继续关注,更多精彩内容即将到来!

被折叠的 条评论
为什么被折叠?



