自学内容网 自学内容网

类与对象、封装、继承、多态

一、类与对象

什么是对象

对象:是一个一个实实在在的,具体的个体(实体)。比如:一个个人、一辆辆车、一本本书等等。

什么是类

类:一组具有相同特征的对象的抽象描述

如:

张三,510220199612013669,18256958568,158936587… 代表一个对象

李四,510220199612013667,18256958575,158936787… 代表一个对象

姓名、身份证号码、手机号码、qq号码… 对应一个类

此时就可以将这些对象抽取相同的特征(属性)封装为一个类

public class Person {
    String name;//名称
    String idCard;//身份证
    String phone;//手机
    String qq;//qq号
}

通俗而言:类就相当于施工图,我们可以根据施工图来知道一栋楼每套房子具有那些功能区(共同的特质),进而造出楼房。

在Java中根据施工图创建对象的关键字是 new。

从代码编写的角度而言,必须先创建类,才能创建出对象。

什么是面向对象

面向对象是一种思想或编程方式。

面向对象的过程是以“对象”为中心。

Scanner input = new Scanner(System.in);//input就是一个Scanner类的对象
 
System.out.print("请输入姓名:");
String name = input.next();
 
System.out.print("请输入年龄:");
int age = input.nextInt();
 
input.close();

与面向对象对应的另一种编程思想:面向过程。它是以函数为中心,实现代码就是通过函数调用把过程串起来。

public class ArrayTools{
    public static int max(int[] arr){
        int max = arr[0];
        for(int i=1; i<arr.length; i++){
            if(arr[i] > max){
                max = arr[i];
            }
        }
        return max;
    }
    
    public static void print(int[] arr){
        for(int i=0; i<arr.length; i++){
            System.out.print(arr[i] + "  ");
        }
        System.out.println();
    }
    
    public static void main(String[] args){
        int[] arr = {2,4,5,3,1};
        print(arr);
        int result = max(arr);
        System.out.println("最大值:" + result);
    }
}

这一段代码,如果抛开ArrayTools类的定义,那么3个函数是独立的,它们互相调用即可,这种方式就是面向过程的编程思想。

另外一个场景描述,来理解面向对象与面向过程的区别:

把大象装进冰箱的问题?

面向过程面向对象
以步骤为中心,即以函数为中心以类/对象为中心
(1)把冰箱门打开 (2)把大象装进去 (3)把冰箱门关上(1)定义人这个类,包含pull,push功能,包含name属性 (2)定义冰箱这个类,包含open,close,save功能,包含size、brand等属性 (3)定义大象这个类,包含walk功能,包含weight属性 (4)定义测试类,包含main方法,在main方法中创建人、冰箱、大象的对象,调用对象的方法来完成

如何定义类

语法格式:

【①修饰符】 ②class ③类名{
    ④类的成员
}

如:

public class Person{
    String name; //类的成员
}

如何new对象

语法格式:

new 类名()

如果没有用变量引用对象,这个对象是一个“匿名对象”。匿名对象都是一次性,无法反复使用

public class Test {
    public static void main(String[] args) {
        new Person();//创建了一个Person类的对象
        System.out.println(new Person());//创建一个Person类的对象,并且打印这个对象
        //com.yang.dto.Person@3b07d329
        System.out.println(new Person());//又创建一个Person类的对象,并且打印这个对象
        //com.yang.dto.Person@41629346
        //上述三个对象是匿名对象,都是独立的,无法重复使用的
 
    }
}

如何用变量引用一个对象?

对象名本质上也是一个变量,是一个引用数据类型的变量。

public class Test {
    public static void main(String[] args) {
        Person p = new Person();
        System.out.println(p);
        System.out.println(p);
        System.out.println(p);
        //p这个对象可以被反复使用
        /*
        这里的p是对象名,同时也变量名
 
        Java的数据类型:
        (1)基本数据类型:byte,short,int,long,float,double,char,boolean
           int a = 1;
        (2)引用数据类型:数组、类等
            int[] arr = new int[5];
            Person p = new Person();
 
            int[],Person是数据类型,从这个角度来说,arr, p也是变量。
            因为这种变量引用的是一个对象,所以这个变量称为引用数据类型的变量,也称为对象名。
 
         */
    }
}

二、封装

封装(Encapsulation)是面向对象编程的三大基本特性之一,它指的是将数据(属性)和行为(方法)捆绑在一起,形成一个对象,并且只通过公开的接口来访问这个对象。封装的目的是为了保护对象的内部状态,防止外部直接访问和修改对象的数据,确保数据的完整性和程序的安全性。
在Java这样的面向对象语言中,封装通常通过使用访问修饰符来控制。例如,使用private关键字修饰的属性或方法只能在类的内部访问,而使用public关键字修饰的属性或方法则可以从类的任何外部访问。
下面是一个简单的Java代码例子,展示了封装的概念:

public class Car {
    // 私有属性,不能直接从类的外部访问
    private String color;
    private int speed;
    // 公开的方法,用于访问私有属性
    public String getColor() {
        return color;
    }
    public void setColor(String color) {
        this.color = color;
    }
    public int getSpeed() {
        return speed;
    }
    public void setSpeed(int speed) {
        if (speed >= 0 && speed <= 120) { // 限制速度的有效性
            this.speed = speed;
        } else {
            System.out.println("Invalid speed!");
        }
    }
    // 公开的方法,执行操作(如开车)
    public void drive() {
        System.out.println("The car is driving with speed " + speed + " km/h.");
    }
}
public class Main {
    public static void main(String[] args) {
        Car myCar = new Car();
        // 通过公共方法设置车辆颜色
        myCar.setColor("Red");
        // 通过公共方法获取车辆颜色
        System.out.println("Car color: " + myCar.getColor());
        // 通过公共方法设置车辆速度
        myCar.setSpeed(60);
        // 通过公共方法执行驾驶操作
        myCar.drive();
    }
}
 在这个例子中,Car类有两个私有属性 color 和 speed,以及几个公开的方法。这些公开的方法提供了控制车辆属性的安全接口。例如,setColor方法用于设置车辆的颜色,而 `setSpeed` 方法用于设置车辆的速度,同时检查速度是否在合理的范围内。这种方式确保了外部代码不能直接访问或修改 color 和 speed属性,必须通过 getColor、setColor、getSpeed 和 setSpeed这些公共方法来间接访问。这样的封装保证了类的内部状态不会被非法操作,同时也保护了代码的完整性。

三、继承

继承是面向对象编程的另一个核心概念,它允许新的类(子类)继承一个现有类(父类)的属性和方法。继承机制使得子类能够重用父类的代码,从而促进代码的复用和模块化。在Java等面向对象的语言中,继承是通过使用继承关键字(如Java中的extends)来实现的。
继承分为两种类型:1. 单继承:一个子类只能继承一个父类。2. 多继承:一个子类可以继承多个父类。不过,在Java这样的语言中,是不支持多继承的,每个类只能有一个基类。
下面是一个简单的Java代码例子,展示了单继承的概念:

// 父类
class Animal {
    protected String name;
    public Animal(String name) {
        this.name = name;
    }
    public void makeSound() {
        System.out.println("The animal makes a sound.");
    }
}
// 子类
class Dog extends Animal {
    public Dog(String name) {
        super(name); // 调用父类的构造函数
    }
    @Override
    public void makeSound() {
        System.out.println("The dog barks.");
    }
}
public class Main {
    public static void main(String[] args) {
        Dog myDog = new Dog("Buddy");
        myDog.makeSound(); // 输出:The dog barks.
    }
}

在这个例子中,Dog 类继承了 Animal类。因此,Dog类自动拥有了 Animal类的所有公共属性和方法。Dog类还可以添加自己特有的属性和方法,或者覆盖(重写)父类的方法,如 makeSound 方法就被 Dog 类覆盖以实现狗的叫声。Animal类中的 name属性被标记为 protected,这意味着它可以在 Animal类的子类中访问。
继承的关系形象地表示了类的层次结构,父类像是模板,而子类则是基于父类模板创建的特定实例。这种模型有助于组织类,使得类的继承体系更加清晰和易于理解。

多态

多态(Polymorphism)是面向对象编程的第三个核心概念,它指的是同一个行为具有多个不同表现形式的特性。在面向对象编程中,多态通常通过继承和接口来实现。多态允许不同类的对象对同一消息做出响应,即同一消息可以根据发送对象的不同而采用不同的处理方式。
多态有两种主要形式:1. 编译时多态(静态多态):这是通过方法重载实现的,方法重载发生在编译时期,编译器根据方法的参数类型和数量来决定调用哪个方法。2. 运行时多态**(动态多态):这是通过继承和接口实现的,运行时根据对象的实际类型来决定调用哪个方法。
下面是一个简单的Java代码例子,展示了运行时多态的概念:

// 父类
class Animal {
    public void makeSound() {
        System.out.println("The animal makes a sound.");
    }
}
// 子类
class Dog extends Animal {
    @Override
    public void makeSound() {
        System.out.println("The dog barks.");
    }
}
class Cat extends Animal {
    @Override
    public void makeSound() {
        System.out.println("The cat meows.");
    }
}
public class Main {
    public static void main(String[] args) {
        Animal myAnimal = new Animal();
        Animal myDog = new Dog();
        Animal myCat = new Cat();
        myAnimal.makeSound(); // 输出:The animal makes a sound.
        myDog.makeSound();    // 输出:The dog barks.
        myCat.makeSound();    // 输出:The cat meows.
        // 编译时多态示例
        makeSound(new Animal()); // 输出:The animal makes a sound.
        makeSound(new Dog());    // 输出:The dog barks.
        makeSound(new Cat());    // 输出:The cat meows.
    }
    // 运行时多态示例
    public static void makeSound(Animal animal) {
        animal.makeSound();
    }
}
  在这个例子中,Animal类有一个 makeSound方法,而 Dog和 Cat类都重写了 makeSound方法。当我们创建 `Animal` 类型的引用指向 Dog或 Cat对象,并调用 makeSound方法时,程序会根据对象的的实际类型来调用相应的 makeSound方法,这就是运行时多态。
  多态性的好处在于它提供了一个接口,使得对新增的子类能够做到“开闭原则”(即对扩展开放,对修改封闭),不需要修改现有的代码即可扩展新的功能。这在设计软件系统时非常有用,可以提高代码的可维护性和可扩展性。

五、总结

总的来说,封装、继承和多态是面向对象编程的三个基本特征,它们有助于创建可重用、可维护和灵活的软件系统。通过这些特征,开发者可以更好地组织代码,提高开发效率,满足不断变化的需求。


原文地址:https://blog.csdn.net/hhgh_/article/details/142771138

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!