一、什么是抽象类

  用abstract修饰的类就是抽象类。抽象类中可以有用abstract修饰的抽象方法,也可以没有抽象方法。

二、为什么要设计抽象类

  在某些情况下,某个父类只是知道其子类应该包含怎样的方法,但无法准确知道这些子类应该如何实现这些方法,于是就定义一些抽象方法,抽象方法是没有方法体的,没有具体的实现,必须要由子类来重写这个方法。例如有个Animal类,它有一个方法eat(),但是不同的动物进食的方式是不同的,所以Animal无法准确知道其子类怎么进食。 那有人会有疑问了,如果父类不知道怎么实现,就不要管这个方法了,让子类自己去扩展好了。但这样会存在一个问题,如果变量的引用类型是父类Animal,实际指向的是子类Dog的实例,那这个类没法调用eat()方法了。

三、抽象类的特征

  • 抽象类必须要用abstract来修饰。
  • 抽象类可以向普通类一样来定义Field、方法(包括普通方法和抽象抽象方法)、构造器、初始化块、内部类。抽象类的构造器只是用于被子类调用,抽象类本身是不可以创建实例的。
  • 含有抽象方法的类只能被定义成抽象类。
package abstractClass;

public abstract class Shape {

    {
System.out.println("执行shape的初始化块。");
} public Shape()
{
System.out.println("shape的无参构造器");
}
public Shape(String color)
{
System.out.println("shape的有参构造器");
this.color = "red";
}
private String color; public static String desc = "shape"; public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
public abstract double calPerimeter(); public abstract String getType(); } 

  上面定义了一个抽象类Shape,再定义一个它的子类Circle,Circle是一个普通类,必须实现Shape中的所有抽象方法。

  

package abstractClass;

public class Circle  extends Shape{

    private double radius;
public Circle(String color, double radius)
{
super(color);
this.radius = radius;
} public double getRadius() {
return this.radius;
} public void setRadius(double radius) {
this.radius = radius;
} @Override
public double calPerimeter() {
return 2 * Math.PI * radius;
} @Override
public String getType() {
return getColor() + "圆形";
}
public static void main(String[] args) {
Shape s = new Circle("黄色", 3);
System.out.println(s.getType());
System.out.println(s.calPerimeter());
} }

  上面的main方法中申明了一个对象s,引用类型是Shape,实际指向的是Circle对象,因为Shape中定义了getType()和calPerimeter()方法,所以在运行的时候程序可以直接调用s变量中的getType()和calPerimeter()方法,无需进行强制类型转换。

  利用抽象类和抽象方法,我们可以更好地发挥多态的优势,是程序更加灵活。

四、abstract不能和final、static、private修饰符共存来修饰方法

  abstract修饰的方法是要被子类重写的,如果一个方法是final的,那这个方法就不能被重写,所以abstract和final不能共存。

  如果一个方法是static修饰的,那么就可以通过类名来直接调用,但是抽象的方法是没有方法体的,这样就会引发错误,所以abstract和static不能共存。

  如果父类的方法是private修饰的,那么这个方法是不能被子类访问的,更不谈重写了,所以abstract和private不能共存。

五、抽象类的作用

  抽象类是从多个具有相同特征的类中抽象出来的一个类,这个抽象类作为父类被继承,其实是子类的一个模板,避免了子类设计的随意性。

  抽象类是模板设计的一种体现,子类在抽象类的基础上进行扩展。

  

【JAVA】抽象类的更多相关文章

  1. java抽象类

    Java 抽象类 在面向对象的概念中,所有的对象都是通过类来描绘的,但是反过来,并不是所有的类都是用来描绘对象的,如果一个类中没有包含足够的信息来描绘一个具体的对象,这样的类就是抽象类. 抽象类除了不 ...

  2. Java接口、Java抽象类、C++抽象类的区别

    由于这三种数据类型都是为了创建类层次结构的顶层构架,且用法有些许相似之处,这里简单区分一下: 接口: 接口用interface关键字定义, 名字一般使用-able形式的形容词. 接口通常定义抽象方法和 ...

  3. java抽象类与接口的区别及用法

    java抽象类与接口的区别及用法 一.抽象类里面的方法可以有实现,但是接口里面的方法确是只能声明. 二.接口是设计的结果 :抽象类是重构的结果 . 三.java不支持多重继承,所以继承抽象类只能继承一 ...

  4. Java 抽象类与接口总结

    一.为什么要使用抽象类?有什么好处? 抽象类是通用接口.不同的子类可以用不同的方法表示此接口.通用接口建立起一种基本形式,以此表示所有子类的共同部分. 必须覆写父类abstract抽象的方法  含有抽 ...

  5. JAVA抽象类和接口的深入探讨

    Java 语言中,抽象类(abstract class) 和接口(interface) 是抽象思想的两种体现形式.初学者很容易把这两者搞混,所以Java面试中考抽象类和接口的区别的面试题也常有出现的. ...

  6. java抽象类和接口的区别(转载)

    1.Java接口和Java抽象类最大的一个区别,就在于Java抽象类可以提供某些方法的部分实现,而Java接口不可以,这大概就是Java抽象类唯一的优点吧,但这个优点非常有用. 如果向一个抽象类里加入 ...

  7. 我对面向对象设计的理解——Java接口和Java抽象类

    在没有好好地研习面向对象设计的设计模式之前,我对Java接口和Java抽象类的认识还是很模糊,很不可理解. 刚学Java语言时,就很难理解为什么要有接口这个概念,虽说是可以实现所谓的多继承,可一个只有 ...

  8. 第十八节:详解Java抽象类和接口的区别

    前言 对于面向对象编程来说,抽象是它的特征之一. 在Java中,实现抽象的机制分两种,一为抽象类,二为接口. 抽象类为abstract class,接口为Interface. 今天来学习一下Java中 ...

  9. Java抽象类和接口的比较

    一个软件设计的好坏,我想很大程度上取决于它的整体架构,而这个整体架构其实就是你对整个宏观商业业务的抽象框架,当代表业务逻辑的高层抽象层结构 合理时,你底层的具体实现需要考虑的就仅仅是一些算法和一些具体 ...

  10. Java - 23 Java 抽象类

    Java 抽象类 在面向对象的概念中,所有的对象都是通过类来描绘的,但是反过来,并不是所有的类都是用来描绘对象的,如果一个类中没有包含足够的信息来描绘一个具体的对象,这样的类就是抽象类. 抽象类除了不 ...

随机推荐

  1. SpringMVC日期参数自动绑定

    Controller: @RequestMapping("/addUser") public String addUser(User user) { ... } Model: pu ...

  2. PT100测温电路经验

    P100电压采集放大电路:前半部分是4.096V恒压源电路,然后是一个桥式电压采样电路,后面是一个电压放大电路. 一 4.096V恒压源电路: 因Vref = 2.5V,故有4.096 = (1 + ...

  3. hdu 5504 GT and sequence

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5504 GT and sequence Time Limit: 2000/1000 MS (Java/O ...

  4. C#学习笔记(一):一些零散但重要的知识点汇总

    集合类型 数组 数组需要注意的就是多维数组和数组的数组之间的区别,如下: using System; namespace Study { class Program { static void Mai ...

  5. Stage3D学习笔记(五):通过矩阵操作纹理

    虽然我们上一节已经实现了正交矩阵的显示,但是可以明显的感觉到要调整显示纹理的坐标和尺寸是相当复杂的,需要对每个顶点进行操作,如果还要加上注册点和旋转的话,用上一节的方法来做是会让人发疯的! 所以我们距 ...

  6. Oracle 中利用闪回查询确定某表在某时间点之后的修改内容,并恢复至该时间点

    Oracle 中利用闪回查询确定某表在某时间点之后的修改内容: 1.查看 DELETE 及 UPDATE 操作修改的数据: SQL> SELECT * FROM tab AS OF TIMEST ...

  7. java实现生产者消费者问题

    引言 生产者和消费者问题是线程模型中的经典问题:生产者和消费者在同一时间段内共用同一个存储空间,如下图所示,生产者向空间里存放数据,而消费者取用数据,如果不加以协调可能会出现以下情况: 生产者消费者图 ...

  8. iOS 时间戳转换为时间

    NSString *str=";//时间戳 NSTimeInterval time=[str doubleValue]+;//因为时差问题要加8小时 == 28800 sec NSDate ...

  9. node.js在windows下的学习笔记(4)---同步,异步,回调的概念

    Node.js是使用事件驱动的,非阻塞的I/O模型,用于构建快速的,可扩展的网络应用程序. Node.js想解决的问题是:处理输入,输入,高并发 1.阻塞与非阻塞 阻塞也叫同步,是指每一次执行一个操作 ...

  10. c# label的内容显示不全

    c# label的内容显示不全.须要设置例如以下属性就可以: 1.将Lable的font属性的字体改成宋体: 2.将AutoSize属性改成true: 然后内容就能够显示所有了.