一、类与对象
- 类:
- 定义:类是一个模板或蓝图,它描述了一类对象共同具有的状态(属性)和行为(方法)。
- 组成:类主要由以下部分组成:
- 成员变量:描述对象的属性或状态(例如:
String name; int age;)。 - 成员方法:描述对象的行为或功能(例如:
eat(),sleep())。 - 构造方法:用于在创建对象时初始化对象。
- 成员变量:描述对象的属性或状态(例如:
- 对象:
- 定义:对象是类的一个具体实例。类是抽象的,对象是具体的。
- 关系:“万物皆对象”。你可以把“类”理解为“汽车设计图”,而“对象”就是根据这张设计图生产出来的一辆辆具体的汽车(比如你的车、我的车)。
示例代码:
// 1. 定义一个“类”
public class Student {// 成员变量(状态/属性)String name;int age;// 构造方法(用于创建对象)public Student(String studentName, int studentAge) {this.name = studentName;this.age = studentAge;}// 成员方法(行为)public void introduce() {System.out.println("大家好,我叫" + name + ",今年" + age + "岁。");}
}// 2. 创建并使用“对象”
public class Main {public static void main(String[] args) {// 使用 'new' 关键字和构造方法创建对象Student student1 = new Student("张三", 20); // student1 是一个对象Student student2 = new Student("李四", 19); // student2 是另一个对象// 调用对象的方法student1.introduce(); // 输出:大家好,我叫张三,今年20岁。student2.introduce(); // 输出:大家好,我叫李四,今年19岁。}
}
二、封装
封装是面向对象的三大特性之一,其核心思想是“隐藏对象的内部细节,仅对外提供公共的访问方式”。
-
目的:
- 提高安全性:防止类的代码和数据被随意访问和修改。
- 易于维护:内部实现细节的改变,只要对外接口不变,就不会影响其他代码。
-
实现方式:
- 使用
private访问修饰符:将成员变量私有化,使其不能在类的外部直接访问。 - 提供公共的
getter和setter方法:通过这些公共方法来读写私有变量,可以在方法中加入逻辑控制(例如,在setAge方法中检查年龄是否合法)。
- 使用
示例代码:
public class Student {// 使用 private 实现封装private String name;private int age;// 公共的 getter 方法,用于获取属性值public String getName() {return name;}// 公共的 setter 方法,用于设置属性值,并可加入逻辑验证public void setName(String name) {this.name = name;}public int getAge() {return age;}public void setAge(int age) {// 在setter中加入控制逻辑if (age > 0 && age < 150) {this.age = age;} else {System.out.println("年龄不合法!");}}
}public class Main {public static void main(String[] args) {Student s = new Student();// s.name = "张三"; // 错误!name 是 private 的,不能直接访问s.setName("张三"); // 正确!通过公共方法访问s.setAge(200); // 输出:年龄不合法! (因为200不在0-150之间)s.setAge(20); // 正确设置System.out.println(s.getName() + ": " + s.getAge() + "岁");}
}
三、继承
继承允许我们基于一个已存在的类来定义一个新类。新类拥有父类的属性和方法,并可以扩展自己的属性和方法。
-
目的:
- 代码复用:子类可以直接使用父类的功能,无需重写。
- 建立类之间的“is-a”关系(例如:
Dogis anAnimal)。
-
关键字:
extends -
特点:
- Java是单继承,一个类只能直接继承一个父类。
- 子类可以重写父类的方法,以实现自身特定的行为。
- 子类不能继承父类的构造方法和被声明为
private的成员。
示例代码:
// 父类
public class Animal {String name;public void eat() {System.out.println(name + "正在吃东西。");}
}// 子类继承父类
public class Dog extends Animal { // Dog 继承自 Animal// 子类可以拥有自己的方法public void bark() {System.out.println(name + "汪汪叫!"); // name 是从父类继承的}// 重写父类的方法@Overridepublic void eat() {System.out.println(name + "正在啃骨头!"); // 狗吃东西的方式不同}
}public class Main {public static void main(String[] args) {Dog myDog = new Dog();myDog.name = "旺财"; // 继承自父类的属性myDog.eat(); // 调用的是子类重写后的方法:输出“旺财正在啃骨头!”myDog.bark(); // 调用子类自己的方法:输出“旺财汪汪叫!”}
}
四、多态
多态是指同一个行为具有多个不同表现形式或形态的能力。简单说就是“父类引用指向子类对象”,调用相同的方法,会根据实际对象的类型产生不同的行为。
-
实现条件:
- 继承
- 方法重写
- 父类引用指向子类对象:
Parent p = new Child();
-
好处:提高了程序的扩展性和可维护性。
示例代码:
// 父类
public class Animal {public void makeSound() {System.out.println("动物发出声音。");}
}// 子类1
public class Cat extends Animal {@Overridepublic void makeSound() {System.out.println("喵喵喵!");}
}// 子类2
public class Duck extends Animal {@Overridepublic void makeSound() {System.out.println("嘎嘎嘎!");}
}public class Main {public static void main(String[] args) {// 多态的典型体现:父类引用指向子类对象Animal animal1 = new Cat();Animal animal2 = new Duck();// 同一个方法调用,实际执行的是子类重写后的方法animal1.makeSound(); // 输出“喵喵喵!”animal2.makeSound(); // 输出“嘎嘎嘎!”// 这种特性使得代码非常灵活Animal[] animals = {new Cat(), new Duck()};for (Animal a : animals) {a.makeSound(); // 无需判断具体类型,程序会自动调用正确的方法}}
}
五、抽象类与接口
抽象类
- 定义:使用
abstract关键字修饰的类。 - 特点:
- 不能实例化:不能直接创建
new AbstractClass()的对象。 - 可以包含抽象方法:使用
abstract修饰,只有声明没有实现的方法(没有方法体{})。子类必须重写所有的抽象方法,除非子类也是抽象类。 - 也可以包含普通方法和成员变量。
- 不能实例化:不能直接创建
- 目的:为一个继承体系提供一个通用的模板,强制子类实现特定的行为。
示例代码:
// 抽象类
public abstract class Shape {// 抽象方法public abstract double calculateArea();// 普通方法public void printInfo() {System.out.println("我是一个形状。");}
}// 子类必须实现抽象方法
public class Circle extends Shape {double radius;@Overridepublic double calculateArea() {return Math.PI * radius * radius;}
}
接口
- 定义:使用
interface关键字定义。在Java 8之前,它完全是抽象方法的集合。现在它可以包含默认方法、静态方法和私有方法。 - 特点:
- 所有方法默认都是
public abstract的(在Java 8之前)。 - 所有变量默认都是
public static final的(常量)。 - 一个类可以实现多个接口(
implements),解决了Java单继承的限制。
- 所有方法默认都是
- 目的:定义一套行为规范,强调“能做什么”,而不关心“如何做”。
示例代码:
// 接口
public interface Flyable {// 抽象方法(默认就是 public abstract)void fly();// Java 8 的默认方法default void repair() {System.out.println("修理飞行装置...");}
}public interface Swimmable {void swim();
}// 类可以实现多个接口
public class Duck extends Animal implements Flyable, Swimmable {@Overridepublic void fly() {System.out.println("鸭子扑棱着翅膀飞。");}@Overridepublic void swim() {System.out.println("鸭子在水里游。");}
}
抽象类 vs 接口
| 特性 | 抽象类 | 接口 |
|---|---|---|
| 定义关键字 | abstract class |
interface |
| 方法 | 可包含抽象方法和具体方法 | Java 8前全是抽象方法;之后可含默认、静态方法 |
| 变量 | 无特殊限制 | 默认是 public static final 常量 |
| 继承 | 单继承(一个类只能继承一个抽象类) | 多实现(一个类可实现多个接口) |
| 设计目的 | “是什么” (is-a),代码复用,模板设计 | “能做什么” (has-a/can-do),定义行为规范 |
| 构造方法 | 有 | 无 |