黑马程序员—java面向对象二

---------------------- android培训java培训、期待与您交流! ----------------------

(一) 继承的概述
多个类中存在相同属性和行为时,将这些内容抽取到单独一个类中,那么多个类无需再定义这些属性和行为,只要继承单独的那个类即可。
多个类可以称为子类,单独这个类称为父类或超类。
子类可以直接访问父类中的非私有的属性和行为。
通过extends关键字让类与类之间产生继承关系。
例:class SubDemo extends Demo{}
继承的出现提高了代码的复用性。
继承的出现让类与类之间产生了关系,提供了多态的前提。
(二) 继承的特点
1、 JAVA只支持单继承,不支持多继承。一个类只能有一个父类,不可以有多个父类。
2、 Java支持多层继承(继承体系)
3、 定义继承需要注意:
不要仅为了获取其他类中某个功能而去继承
类与类之间要有所属(“is a”)关系,xx1是xx2的一种。
(三) super关键字
super和this的用法相同
this代表本类引用
super代表父类引用
当子父类出现同名成员时。可以用super进行区分
子类要调用父类构造函数时,可以使用super语句。
(四) 函数覆盖(override)
子类中出现与父类一模一样的方法时,会出现覆盖操作,也称为重写或复写。
父类中私有方法不可以被覆盖
在子类覆盖方法中,继续使用被覆盖的方法可以通过super.函数名获取
覆盖注意事项:
覆盖时,子类方法权限一定要大于等于父类方法权限
静态只能覆盖静态。
覆盖的应用:
当子类需要父类的功能,而功能主体子类有自己特有内容时,可以复写父类中的方法,这样,即沿袭了父类的功能,又定义了子类特有的内容。
(五) 子类的实例化过程
子类中所有的构造函数默认都会访问父类中空参数的构造函数
因为每一个构造函数 的第一行都有一条默认的语句super();
子类会具备父类中数据,所以要先明确父类是如何对这些数据初始化的。
当父类中没有空参数的构造函数时,子类的构造函数必须通过this或者super语句要访问的构造函数。
(六) final关键字
final可以修饰类,方法,变量。
final修饰的类不可以被继承。
final修饰的方法不可以被覆盖。
final修饰的变量是一个常量。只能被赋值一次。
内部类只能访问被final修饰的局部变量。
(七) 抽象类
1、抽象类概述
抽象定义:
抽象就是多个事物中将共性的,本质的内容抽取出来。
抽象类:
java中可以定义没有方法体的方法,该方法的具体实现由子类完成,该方法称为抽象方法,包含抽象方法的类就是抽象类。
抽象方法的由来:
多个对象都具备相同的功能,但是功能具体内容有所不同,那么在抽取过程中,只抽取了功能定义,并未抽取功能主体,那么只有功能申明,没有功能主体的方法称为抽象方法。
2、抽象类特点
抽象类和抽象方法必须用abstract关键字来修饰。
抽象方法只有方法申明,没有方法体,定义在抽象类中。
格式:修饰符 abstract 返回值类型 函数名(参数列表);
抽象类不可以被实例化,也就是不可以用new创建对象。原因如下:
抽象类是具体事物抽取出来的,本身是不具体的,没有对应的实例。而且抽象类即时创建了对象,调用抽象方法也没有意义。
抽象类通过其子类实例化,而子类需要覆盖掉抽象类中所有的抽象方法后才可以创建对象,否则该子类也是抽象类。
(八) 接口
格式:interface 接口名 {}
接口中的成员修饰符是固定的。
成员常量:public static final
成员函数:public abstract
接口的出现将“多继承”通过另一种形式体现来,即“多事项”。
接口的特点
接口是对外暴露的规则。
接口是程序的功能扩展。
接口可以用来多实现。
类与接口之间是实现关系,而且类可以继承一个类的同时实现多个接口。
接口与接口之间可以有继承关系。
(九) 内部类
将一个类定义在另一个类的里面,对里面那类就称为内部类。
1、访问特点:
内部类可以直接访问外部类中的成员,包括私有成员。
而外部类要访问内部类中的成员必须要建立内部类的对象。
2、内部类的位置
内部类定义在成员位置上
可以被private static成员修饰符修饰。
被static修饰的内部类只能访问外部类中的静态成员
内部类定义在局部位置上
也可以直接访问外部类的成员。
同时可以访问所在局部的局部变量,但必须是被final修饰的。
3、匿名内部类
就是内部类的简化写法。
前提:内部类可以继承或实现一个外部类或接口。
格式:new 外部类名或接口名(){覆盖类或接口中的代码,(也可以自定义内容。)}
简单理解:就是建立一个带内容的外部类或者接口的子类匿名对象。
(十) 异常
1、异常的体系
Throwable
Error:通过出现重大问题如:运行的类不存在或内存溢出等。
Exception:在运行时运行出现的一起情况,可以通过try catch finally
Exception 和Error的子类名都是以父类名作为后缀。
Throwable中的方法
getMessage():获取异常信息,返回字符串。
toString():获取异常名和异常信息,返回字符串。
printStackTrace():获取异常名和异常信息,以及异常出现在程序中的位置,返回值void。
printStackTrace(PrintSteam s):通常用该方法将异常内容保存在日志文件,以便查阅。
2、throws 和throw
throws用于标识函数暴露出额异常。
throw用于抛出异常对象。
throws与throw的区别:throws用在函数上,后面跟异常类名;throw用在函数内,后面跟异常对象。
3、异常处理
try
{
需要检测的代码;
}
catch(异常类 变量)
{
异常处理代码;
}
finally
{
一定会执行的代码;
}
finally代码只有一种情况不会被执行,就是在之前执行了System.exit(0)。
4、自定义异常
自定义类继承Exception或其子类
通过构造函数定义异常信息。
例:
class DemoException extends Exception
{
DemoException(String message)
{
super(message);
}
}
通过throw将自定义异常抛出。
5、异常细节
RuntimeException以及其子类如果在函数中被throw抛出,可以不在函数上申明。
一个方法被覆盖时,覆盖它的方法必须抛出相同的异常或异常的子类。
如果父类抛出多个异常,那么重写方法必须抛出 那些异常的一个子集,不能抛出新的异常。
介绍异常在分层设计时的层内封装。
(十一)包(package)
对类文件进行分类管理。
给类提供多层命名空间。
写在程序文件的第一行。
类名的全称的是 包名.类名
包也是一种封装形式。
1、 包之间的访问
被访问的包中的类权限必须是public的
类中的成员权限:public或protected
protected是为其他包 中的子类提供的一种权限。
2、四种权限
public protected default private
同一类中 是 是 是 是
同一包中 是 是 是
子类 是 是
不同包中 是
(十二)import关键字与jar包
1、import关键字
简化类名。
一个程序文件中只有一个package,可以有多个import。
用来导包中的类,不导入包中的包
2、 jar包
java的压缩包
方便项目的携带。
方便使用,只要在classpath设置jar路径即可。
数据库驱动,SSH框架等都是以jar包体现的。
jar包的操作:
通过jar.exe工具对jar的操作。
创建jar包:jar –cvf mypack.jar packa packb
查看jar包:jar –tvf mypack.jar [>定向文件]
解压缩:jar -xvf mypack.jar
自定义jar包的清单文件:jar –cvfm mypack.jar mf.txt packa packb
(十二)多态
多态是java面向对象中一个重要的概念,它也是事物存在的多种体现形态。比如一个简单的例子,在动物这个大的类中,包含有许多不同的物种,我们可以称一只猫为猫,我们也可以说它是动物,这是很显然的,这里面就涉及到多态的概念了。
多态在java中强调的是对象上的体现,其实多态在java中除了在对象上有体现外,其他也是有体现的,比如函数,重载和覆盖其实就是函数多态性的体现。那么,我们应围绕哪几点对多态进行学习呢?从多态的特点来讲,我们应从以下四个方面进行学习。
1 多态的表现形式
在java中我们经常要描述对象,当我们在描述一些具有相同特征的对象时我们就会抽取其相同的部分,然后就能提高代码整体的可用性。比如我们在描述几种不同的动物的基本行为时,我们就可以进行向上的抽取,如下面的示例代码:
abstract class Animal
{
public abstract void eat();
}
class Cat extends Animal
{
public void eat()
{
System.out.println("chiyu");
}
public void CatchMouse()
{
System.out.println("catch mouse");
}
}
class Dog extends Animal
{
public void eat()
{
System.out.println("chigutou");
}
public void KanJia()
{
System.out.println("kanjia");
}
}
class DuoTaiDemo
{
public static void main(String[] args)
{
Cat c = new Cat();
c.eat();
Dog d = new Dog();
d.eat();
Cat c1 = new Cat();
c1.eat();
Cat c2 = new Cat();
c2.eat();

}
}
在上面的代码中我们可以看出,在主函数中,每种动物要想实现eat方法就得先new个对象,然后再调用eat方法(如c,d),即便是同一种动物的不同个体也仍然如此(如c,c1,c2),这样代码的复用性就很差了。基于此,我们就可以用多态来表现,并用他们的父类Animal来抽取共性方法,相应的代码如下:
public static void function(Animal a)//Animal a = new Cat();
{
a.eat();
}
这样在主函数中直接用调用此方法后就可以了,这就提高了程序的扩展性和代码的复用性,因为在后续的任何动物中都可以直接调用,如function(new Cat());function(new Dog());等等。

2 多态的前提
通过的上面的示例我们知道多态必须是类与类有继承或者类与接口有实现关系时才可以,通常还有一个前提也即存在覆盖,这是很显然的,因为如果没有覆盖,在上例中我们在多态后怎么来调用子类共同的eat方法,这样显然就没意义了,这里也暴露出多态的一个弊端,也即只能是父类的引用调用父类的方法。
3 多态的好处
从1中我们就可以看出多态的两个好处,一个是提高功能的扩展,一个是提高了代码的复用。
4 多态如何应用
那么,对于多态我们如何来应用呢?我们知道在多态后我们可以调用父类的方法类实现功能,那么我们怎么来实现每个子类特有的方法呢?这就要就行类型的转换,也即当我们欲调用子类的特有方法时,可以通过代码:Cat c = (Cat) a;来实现类型的向下转型,然后再调用子类特有的方法。
所以,我们可以看出,多态一直都是针对子类对象在做变化,我们能转换的是父类的引用指向自己的子类对象时,该引用可以被提升,也可以被强制转换。
最后,总结一下多态中成员函数具有的特点,结合上面的程序对于语句 Animal a = new Cat();在编译时期,我们应该看引用型变量所属的类中是否有调用的方法,如果有,编译通过,否则,编译是失败的;而在运行时期,我们应看对象所属的类中是否有被调用的方法,有则运行通过,否则失败。一句话表述就是:成员函数在多态调用时,编译看左边,运行看右边。

多个类中存在相同属性和行为时,将这些内容抽取到单独一个类中,那么多个类无需再定义这些属性和行为,只要继承单独的那个类即可。
多个类可以称为子类,单独这个类称为父类或超类。
子类可以直接访问父类中的非私有的属性和行为。
通过extends关键字让类与类之间产生继承关系。
例:class SubDemo extends Demo{}
继承的出现提高了代码的复用性。
继承的出现让类与类之间产生了关系,提供了多态的前提。
(二) 继承的特点
1、 JAVA只支持单继承,不支持多继承。一个类只能有一个父类,不可以有多个父类。
2、 Java支持多层继承(继承体系)
3、 定义继承需要注意:
不要仅为了获取其他类中某个功能而去继承
类与类之间要有所属(“is a”)关系,xx1是xx2的一种。
(三) super关键字
super和this的用法相同
this代表本类引用
super代表父类引用
当子父类出现同名成员时。可以用super进行区分
子类要调用父类构造函数时,可以使用super语句。
(四) 函数覆盖(override)
子类中出现与父类一模一样的方法时,会出现覆盖操作,也称为重写或复写。
父类中私有方法不可以被覆盖
在子类覆盖方法中,继续使用被覆盖的方法可以通过super.函数名获取
覆盖注意事项:
覆盖时,子类方法权限一定要大于等于父类方法权限
静态只能覆盖静态。
覆盖的应用:
当子类需要父类的功能,而功能主体子类有自己特有内容时,可以复写父类中的方法,这样,即沿袭了父类的功能,又定义了子类特有的内容。
(五) 子类的实例化过程
子类中所有的构造函数默认都会访问父类中空参数的构造函数
因为每一个构造函数 的第一行都有一条默认的语句super();
子类会具备父类中数据,所以要先明确父类是如何对这些数据初始化的。
当父类中没有空参数的构造函数时,子类的构造函数必须通过this或者super语句要访问的构造函数。
(六) final关键字
final可以修饰类,方法,变量。
final修饰的类不可以被继承。
final修饰的方法不可以被覆盖。
final修饰的变量是一个常量。只能被赋值一次。
内部类只能访问被final修饰的局部变量。
(七) 抽象类
1、抽象类概述
抽象定义:
抽象就是多个事物中将共性的,本质的内容抽取出来。
抽象类:
java中可以定义没有方法体的方法,该方法的具体实现由子类完成,该方法称为抽象方法,包含抽象方法的类就是抽象类。
抽象方法的由来:
多个对象都具备相同的功能,但是功能具体内容有所不同,那么在抽取过程中,只抽取了功能定义,并未抽取功能主体,那么只有功能申明,没有功能主体的方法称为抽象方法。
2、抽象类特点
抽象类和抽象方法必须用abstract关键字来修饰。
抽象方法只有方法申明,没有方法体,定义在抽象类中。
格式:修饰符 abstract 返回值类型 函数名(参数列表);
抽象类不可以被实例化,也就是不可以用new创建对象。原因如下:
抽象类是具体事物抽取出来的,本身是不具体的,没有对应的实例。而且抽象类即时创建了对象,调用抽象方法也没有意义。
抽象类通过其子类实例化,而子类需要覆盖掉抽象类中所有的抽象方法后才可以创建对象,否则该子类也是抽象类。
(八) 接口
格式:interface 接口名 {}
接口中的成员修饰符是固定的。
成员常量:public static final
成员函数:public abstract
接口的出现将“多继承”通过另一种形式体现来,即“多事项”。
接口的特点
接口是对外暴露的规则。
接口是程序的功能扩展。
接口可以用来多实现。
类与接口之间是实现关系,而且类可以继承一个类的同时实现多个接口。
接口与接口之间可以有继承关系。
(九) 内部类
将一个类定义在另一个类的里面,对里面那类就称为内部类。
1、访问特点:
内部类可以直接访问外部类中的成员,包括私有成员。
而外部类要访问内部类中的成员必须要建立内部类的对象。
2、内部类的位置
内部类定义在成员位置上
可以被private static成员修饰符修饰。
被static修饰的内部类只能访问外部类中的静态成员
内部类定义在局部位置上
也可以直接访问外部类的成员。
同时可以访问所在局部的局部变量,但必须是被final修饰的。
3、匿名内部类
就是内部类的简化写法。
前提:内部类可以继承或实现一个外部类或接口。
格式:new 外部类名或接口名(){覆盖类或接口中的代码,(也可以自定义内容。)}
简单理解:就是建立一个带内容的外部类或者接口的子类匿名对象。
(十) 异常
1、异常的体系
Throwable
Error:通过出现重大问题如:运行的类不存在或内存溢出等。
Exception:在运行时运行出现的一起情况,可以通过try catch finally
Exception 和Error的子类名都是以父类名作为后缀。
Throwable中的方法
getMessage():获取异常信息,返回字符串。
toString():获取异常名和异常信息,返回字符串。
printStackTrace():获取异常名和异常信息,以及异常出现在程序中的位置,返回值void。
printStackTrace(PrintSteam s):通常用该方法将异常内容保存在日志文件,以便查阅。
2、throws 和throw
throws用于标识函数暴露出额异常。
throw用于抛出异常对象。
throws与throw的区别:throws用在函数上,后面跟异常类名;throw用在函数内,后面跟异常对象。
3、异常处理
try
{
需要检测的代码;
}
catch(异常类 变量)
{
异常处理代码;
}
finally
{
一定会执行的代码;
}
finally代码只有一种情况不会被执行,就是在之前执行了System.exit(0)。
4、自定义异常
自定义类继承Exception或其子类
通过构造函数定义异常信息。
例:
class DemoException extends Exception
{
DemoException(String message)
{
super(message);
}
}
通过throw将自定义异常抛出。
5、异常细节
RuntimeException以及其子类如果在函数中被throw抛出,可以不在函数上申明。
一个方法被覆盖时,覆盖它的方法必须抛出相同的异常或异常的子类。
如果父类抛出多个异常,那么重写方法必须抛出 那些异常的一个子集,不能抛出新的异常。
介绍异常在分层设计时的层内封装。
(十一)包(package)
对类文件进行分类管理。
给类提供多层命名空间。
写在程序文件的第一行。
类名的全称的是 包名.类名
包也是一种封装形式。
1、 包之间的访问
被访问的包中的类权限必须是public的
类中的成员权限:public或protected
protected是为其他包 中的子类提供的一种权限。
2、四种权限
public protected default private
同一类中 是 是 是 是
同一包中 是 是 是
子类 是 是
不同包中 是
(十二)import关键字与jar包
1、import关键字
简化类名。
一个程序文件中只有一个package,可以有多个import。
用来导包中的类,不导入包中的包
2、 jar包
java的压缩包
方便项目的携带。
方便使用,只要在classpath设置jar路径即可。
数据库驱动,SSH框架等都是以jar包体现的。
jar包的操作:
通过jar.exe工具对jar的操作。
创建jar包:jar –cvf mypack.jar packa packb
查看jar包:jar –tvf mypack.jar [>定向文件]
解压缩:jar -xvf mypack.jar
自定义jar包的清单文件:jar –cvfm mypack.jar mf.txt packa packb
(十二)多态
多态是java面向对象中一个重要的概念,它也是事物存在的多种体现形态。比如一个简单的例子,在动物这个大的类中,包含有许多不同的物种,我们可以称一只猫为猫,我们也可以说它是动物,这是很显然的,这里面就涉及到多态的概念了。
多态在java中强调的是对象上的体现,其实多态在java中除了在对象上有体现外,其他也是有体现的,比如函数,重载和覆盖其实就是函数多态性的体现。那么,我们应围绕哪几点对多态进行学习呢?从多态的特点来讲,我们应从以下四个方面进行学习。
1 多态的表现形式
在java中我们经常要描述对象,当我们在描述一些具有相同特征的对象时我们就会抽取其相同的部分,然后就能提高代码整体的可用性。比如我们在描述几种不同的动物的基本行为时,我们就可以进行向上的抽取,如下面的示例代码:
abstract class Animal
{
public abstract void eat();
}
class Cat extends Animal
{
public void eat()
{
System.out.println("chiyu");
}
public void CatchMouse()
{
System.out.println("catch mouse");
}
}
class Dog extends Animal
{
public void eat()
{
System.out.println("chigutou");
}
public void KanJia()
{
System.out.println("kanjia");
}
}
class DuoTaiDemo
{
public static void main(String[] args)
{
Cat c = new Cat();
c.eat();
Dog d = new Dog();
d.eat();
Cat c1 = new Cat();
c1.eat();
Cat c2 = new Cat();
c2.eat();

}
}
在上面的代码中我们可以看出,在主函数中,每种动物要想实现eat方法就得先new个对象,然后再调用eat方法(如c,d),即便是同一种动物的不同个体也仍然如此(如c,c1,c2),这样代码的复用性就很差了。基于此,我们就可以用多态来表现,并用他们的父类Animal来抽取共性方法,相应的代码如下:
public static void function(Animal a)//Animal a = new Cat();
{
a.eat();
}
这样在主函数中直接用调用此方法后就可以了,这就提高了程序的扩展性和代码的复用性,因为在后续的任何动物中都可以直接调用,如function(new Cat());function(new Dog());等等。

2 多态的前提
通过的上面的示例我们知道多态必须是类与类有继承或者类与接口有实现关系时才可以,通常还有一个前提也即存在覆盖,这是很显然的,因为如果没有覆盖,在上例中我们在多态后怎么来调用子类共同的eat方法,这样显然就没意义了,这里也暴露出多态的一个弊端,也即只能是父类的引用调用父类的方法。
3 多态的好处
从1中我们就可以看出多态的两个好处,一个是提高功能的扩展,一个是提高了代码的复用。
4 多态如何应用
那么,对于多态我们如何来应用呢?我们知道在多态后我们可以调用父类的方法类实现功能,那么我们怎么来实现每个子类特有的方法呢?这就要就行类型的转换,也即当我们欲调用子类的特有方法时,可以通过代码:Cat c = (Cat) a;来实现类型的向下转型,然后再调用子类特有的方法。
所以,我们可以看出,多态一直都是针对子类对象在做变化,我们能转换的是父类的引用指向自己的子类对象时,该引用可以被提升,也可以被强制转换。
最后,总结一下多态中成员函数具有的特点,结合上面的程序对于语句 Animal a = new Cat();在编译时期,我们应该看引用型变量所属的类中是否有调用的方法,如果有,编译通过,否则,编译是失败的;而在运行时期,我们应看对象所属的类中是否有被调用的方法,有则运行通过,否则失败。一句话表述就是:成员函数在多态调用时,编译看左边,运行看右边。

--------------------- android培训java培训、期待与您交流! ----------------------

详细请查看:http://edu.csdn.net/heima

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值