黑马程序员技术交流社区
标题:
为什么要在定义抽象类时使用abstract关键字
[打印本页]
作者:
乔兵
时间:
2013-10-9 07:32
标题:
为什么要在定义抽象类时使用abstract关键字
本帖最后由 乔兵 于 2013-10-9 07:33 编辑
众所周之,在任何面向对象的语言中(包括
Java
、
C#
),在定义抽象类时必须使用
abstract
关键字。虽然这已经习已为常了,但实际上
abstract
是为了在实现接口或继承抽象类避免歧议而必须存在的。
看如下代码:
abstract class Class1
{
abstract void method();
}
复制代码
上面的代码是一个典型的抽象类,在定义类时和定义方法时都使用了
abstract
。但从编译器的角度来说,在定义类时完全可以不使用
abstract
,如下面的代码所示:
class Class1
{
abstract void method();
}
复制代码
对于上面的代码,编译器在编译时并不会产生奇异,只要检测到类中有一个用
abstract
关键字的代码,就可以在编译的过程中自动向
Class1
添加
abstract
,也就是说,在定义
Class1
时添加
abstract
的工作应该由编译器来完成。
虽然上面的过程看起来没什么问题,也并不难实现,但各位不要忘了,实现抽象类除了上面的方式,还有另外一种方式,这就是实现接口,而并不实现接口中的所有方法。看下面的代码:
interface MyInterface
{
public void method1();
public void method2();
}
abstract class MyClass implements MyInterface
{
public void method1()
{
}
}
复制代码
上面代码中
MyClass
类并未实现
method2
方法,也并示在定义方法时使用
abstract
关键字,然后,
method2
方法实际上就是
abstract
方法。
大家可以想象,如果在定义抽象类时不使用
abstract
关键字会怎么样呢?看下面的代码:
interface MyInterface
{
public void method1();
public void method2();
}
class MyClass implements MyInterface
{
public void method1()
{
}
}
复制代码
上面的代码一定会编译出错的,因为编译器蒙了。在面向对象语言中规定,一个普通类必须实现接口中的所有方法。而在上面的代码中,
method2
方法未实现。而编译器无法判断
MyClass
类是抽象类,还是普通类。如果按着普通类来处理,则会编译出错,如果按着抽象类来处理,则完全符合面向对象规则。因此,就产生了歧议。当编译器在编译源代码时,一定会产生错误,否则可能会编译成和源代码的含义不同的二进制目标文件。
当然,上面的代码也可以设置默认的规则,也就是按着普通类处理不通过时,就按着抽象类来处理。但这又会带来另一个问题。如果开发人员忘记实现某个接口的方法,那不是这个类就会被编译器认为是抽象类了吗?因此,为了保险起见,编译器的设计者特意为抽象类指定一个
abstract
关键字,也就是说,这个类是否是抽象类,应由开发人员通过编码的方式来指定,而不是由编译器自做主张。
从上面的描述可以看出,加
abstract
关键字主要是为了避免普通类在实现接口时产生的歧议。如果假设面向对象语言中没有接口,
abstract
关键字完全可以去掉。当然,继承抽象类也和实现接口类似。
象面向对象语言中的静态方法很多就没有静态类的概念(
Java
没有,
C#
有)。因此,在定义类时加不加
static
,并不会产生奇异,所以
static
关键字在定义静态类时也就不是必须的了。
(转自blogjava)
作者:
murder_fol
时间:
2013-10-9 08:39
谢谢分享,很不错,每天看些这样帖子,可以复习,还可以长知识
欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/)
黑马程序员IT技术论坛 X3.2