java 、abstract修饰的【抽象类】【比如几何图形类】

现实中问题引入

现实中一类具有共同特征的类,但是无法具体实现。,比如我们定义了一个几何类,叫做Shape,我们有一个方法要计算周长,直接在每个子类实现虽然可以,但是无法通过Shape定义的实例来访问到这个计算周长的方法了。

抽象类和抽象方法:

抽象类和抽象方法都必须使用abstract修饰符来定义,有抽象方法的类只能被定义成抽象类,抽象类里面可以没有抽象方法。

具体规则如下:

1)抽象类必须用abstract修饰符修饰;

2)抽象方法也必须用abstract修饰符修饰;

3)抽象方法不能有方法体

4)抽象类不能被实例化,不能用new创建实例。

5)含有抽象方法的类,只能被定义成抽象类

语法:abstract 修饰

例如:平面图形类/三角形类

package com.zmd.study.abstract_example;

/**
 * @ClassName PlaneFigure
 * @projectName: object1
 * @author: Zhangmingda
 * @description: 抽象一个平面图形类,都有获取类型和周长的方法
 * date: 2021/3/30.
 */
public abstract class PlaneFigure {
    /**
     * 获取平面图形的类型
     */
    public abstract String getType();

    /**
     * 获取平面图形的周长
     */
    public abstract double getPerimeter();
}

三角形类继承抽象类平面图形类

package com.zmd.study.abstract_example;

/**
 * @ClassName Triangle
 * @projectName: object1
 * @author: Zhangmingda
 * @description: XXX
 * date: 2021/3/30.
 */
public class Triangle extends PlaneFigure {
    /**
     * 三角形的三边长类型定义
     */
    private double a;
    private double b;
    private double c;

    /**
     * 构造方法,创建三角形实例必须提供三边长度
     */
    public Triangle(double a, double b, double c) {
        /**
         *@params [a, b, c] 三角形三边长度
         *@return null
         *@创建时间 2021/3/30
         */
        if(a+b < c || a+c < b || b+c < a){
            System.out.println("Failed!:三角形的两边之和必须大于第三边");
            return;
        }
        this.a = a;
        this.b = b;
        this.c = c;
    }

    @Override
    public String getType() {
        if(a+b < c || a+c < b || b+c < a){return "未知图形";}
        return "三角形";
    }

    @Override
    public double getPerimeter() {
        return a + b + c;
    }


}

测试类

package com.zmd.study.abstract_example;

public class AbstractTesst {
    public static void main(String[] args) {
        PlaneFigure planeFigure = new Triangle(3,4,5);
        System.out.println(planeFigure.getType());
        System.out.println(planeFigure.getPerimeter());
    }
    /**
     * 三角形
     * 12.0
     */
}

抽象类的作用

 抽象类只能被当成父类来继承,抽象类是从多个具体类中抽象出来的父类。。是从多个具有相同特征的类中抽象出来的一个抽象类,可以作为子类的模板,从而避免子类涉设计的随意性。

抽象类是一种模板设计思路,抽象类作为多个子类的通用模板,子类在抽象类的基础上进行扩展和改造。实际应用中子类总体上会大致保留抽象类的行为方式。

 

汽车抽象类 和具体车型类案例

目录树:

Vehicle:

  -Vehicle.java //汽车抽象类

  -Car.java 

  -Bus.java

  -CarType.java  //小汽车枚举类型

  VehicleTest.java

 

// Vehicle.java

package Vehicle;

public abstract class Vehicle {//用abstract 修饰的类叫做抽象类
    //用abstract 修饰的方法叫做抽象方法,没有方法体
    public abstract double getRent(int days);
}
//CarType.java 

package Vehicle;
/**
 * @author: Zhangmingda
 * @description:自定义车型:两箱、三箱,SUV、MPV 等,
 *  可以看做是一组常量的组合,类似一年只有四个季度
 * date: ${DATE}.
 */
public enum  CarType {
    HATCHBACK,THREECOMPARTMENT, SUV, MPV
    //分别代表两箱,三箱,SUV,MPV(商务车)
}

//Car.java

//Car.java

package Vehicle;

public class Car extends Vehicle{
    CarType type; //使用枚举类型避免出错

    //重写父类的抽象方法
    @Override
    public double getRent(int days) {
        switch (type){
            case HATCHBACK://IDEA智能识别自定义的枚举可选类型
                return 200 * days;
            case THREECOMPARTMENT:
                return 300 *days;
            case SUV:
                return 350 * days;
            case MPV:
                return 150 * days;
            default:
                return 800 * days;
        }
    }
}

 

//Bus.java

package Vehicle;

/**
 * @author: Zhangmingda
 * @description: XXX
 * date: 2019/12/3.
 */
public class Bus extends Vehicle{
    //大巴车定义自己的座位数属性
    int seats;
    //重写父类的抽象方法父类要求返回double类型,子类则也要求返回double
    @Override
    public double getRent(int days) {
        if(seats > 0 && seats <= 18){
            return 400 * days;  //不同的座位数每日租金不同,返回计算结果不同
        }else if(seats > 18 && seats <= 25 ){
            return 1000 * days;
        }else if(seats > 25 && seats <= 51 ) {
            return 1500 * days;
        }else{
            return 2000 *days;
        }

    }
}

 

//VehicleTest.java


package Vehicle;
import java.util.Scanner;
/**
 * @author: Zhangmingda
 * @description: 测试不同车的租金
 * date: 2019/12/3.
 */
public class VehicleTest {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        //选中代码,快捷键Ctrl + Alt + T 用代码包裹
        while (true) {
            System.out.print("请输入要选择的种类:\n1 小汽车、2 Bus 7座以上汽车 3 退出:");
            int chose = sc.nextInt();
            if(chose == 1){
                Car car = new Car();
                System.out.print("请选择汽车车型:1、两箱 2、三箱 3、SUV 4、PMV(商务)");
                chose = sc.nextInt();
                //根据选择计算租金
                switch (chose){
                    case 1:
                        car.type = CarType.HATCHBACK;break;
                    case 2:
                        car.type = CarType.THREECOMPARTMENT;break;
                    case 3:
                        car.type = CarType.SUV;break;
                    case 4:
                        car.type = CarType.MPV;break;
                    default:
                        System.out.println("输入有误!以三箱做计算");
                        car.type = CarType.THREECOMPARTMENT;
                        break;
                }
                //车型信息确定。开始计算租金。这里定义一个单独的方法来计算,和计算bus车型共用
                calculate(car);
            }else if(chose == 2) {
                //确定选择bus的作为数
                Bus bus = new Bus();
                System.out.print("请选择作为数:1、18座 2、 19-25座 3、26-51座: " );
                chose = sc.nextInt();
                bus.seats = chose;
                //车型信息确定。开始计算租金。这里定义一个单独的方法来计算,和计算bus车型共用
                calculate(bus);
            }else {
                //return;
                System.exit(0);//退出JVM虚拟机
            }
        }

    }

    private static void calculate(Vehicle vehicle) {
        Scanner scanner = new Scanner(System.in);
        System.out.print("请输入要租用的天数:");
        int days = scanner.nextInt();
        System.out.println("您的租金为:" + vehicle.getRent(days) );

    }
}

 

//模拟计算机USB接口应用
//目录usb
// Computer.java 计算机类
// Disk.java 磁盘类实现USB接口
// Printer.java 打印机类 实现USB接口
// Usb.java 接口规范
// 接口
package usb;

/**
 * @author: Zhangmingda
 * @description: 定义一个接口,供任何USB设备相互对接
 * date: 2019/12/3.
 */
public interface Usb {
    void connect();
    void disconnect();
}

package usb;

/**
 * @author: Zhangmingda
 * @description: XXX
 * date: 2019/12/3.
 */
public class Printer implements Usb {
    @Override
    public void connect() {
        System.out.println("打印机已连接。");
    }

    @Override
    public void disconnect() {
        System.out.println("打印机已断开连接,可以拔出了!");
    }
}
package usb;

/**
 * @author: Zhangmingda
 * @description: XXX
 * date: 2019/12/3.
 */
public class Disk implements Usb {
    @Override
    public void connect() {
        System.out.println("硬盘已连接。");
    }

    @Override
    public void disconnect() {
        System.out.println("硬盘已断开连接,可以拔出了!");
    }
}
package usb;

/**
 * @author: Zhangmingda
 * @description: 定义计算机可以插入USB设备、移除USB设备功能
 * date: 2019/12/3.
 */
public class Computer {
      Usb slot; //定义Usb 插槽,类变量
    //把USB设备插入USB卡槽,需要通过参数接收一个USB设备,实现了一个USB接口就行
    public void insert( Usb device){
        slot = device;//通过赋值模拟设备插在USB口中
        slot.connect();//插上就自动连接
    }
    public void pullout(Usb device){
        if(this.slot == null){
            System.out.println("USB口没有设备");
            return;
        }
        device.disconnect();
        this.slot = null;
        System.out.println("设备已拔出");
    }
}
package usb;

/**
 * @author: Zhangmingda
 * @description: 测试计算机插拔 实现接口的设备
 * date: 2019/12/3.
 */
public class ComputerTest {
    public static void main(String[] args) {
        //建立一个计算机对象、磁盘、打印机
        Computer computer = new Computer();
        Disk disk = new Disk();
        Printer printer = new Printer();
        //模拟插入拔出操作
        computer.insert(disk);
        computer.pullout(disk);
        computer.insert(printer);
        computer.pullout(printer);
        computer.pullout(printer);

    }
}

 

 

 

posted on 2019-12-03 15:33  zhangmingda  阅读(653)  评论(0编辑  收藏  举报

导航