黑马程序员java学习日记——面向对象(三)
来源:互联网 发布:直播摄像头美颜软件 编辑:程序博客网 时间:2024/05/21 19:33
------- android培训、java培训、期待与您交流! ----------
一、 抽象类
(1)抽象:把多个类中的共性的内容进行抽取,抽取后就能形成一个继承体系。但是,在今天的案例中,方法的声明相同,方法体不同,这样的抽取后,在父类中定义的时候,是不能写方法体的,这样的方法要想被java识别,就必须被标记为抽象的。如果一个类有抽象方法,那么该类肯定是抽象类。反之,抽象类中不一定有抽象方法。
抽象类的由来:
多个对象都具备相同的功能,但是功能具体内容有所不同,那么在抽取过程中,只抽取了功能定义,并未抽取功能主体,那么只有功能声明,没有功能主体的方法称为抽象方法。
例如:狼和狗都有吼叫的方法,可是吼叫内容是不一样的。所以抽象出来的犬科虽然有吼叫功能,但是并不明确吼叫的细节。
(2)格式:
抽象方法只有方法声明,没有方法体,定义在抽象类中。
格式:修饰符 abstract返回值类型 函数名(参数列表);
(2)好处:
A:抽象类中可以有成员变量和非抽象方法,也可以实现代码的复用。
B:抽象类强制要求继承他的子类必须完成某些功能。
(3)成员特点:
A:构造方法
抽象类有构造方法,但是本身不能被实例化。
它的构造方法用于子类实例化使用。
B:成员变量
抽象类既可以有成员变量,也可以有成员常量。
C:成员方法
抽象类既可以抽象方法,也可以有非抽象方法。
代码示例:
abstract class Animal{private String name;public final int x = 10;public Animal(){System.out.println("animal");}public Animal(String name){this.name = name;}public void setName(String name){this.name = name;}public String getName(){return name;}public void show(){System.out.println("今天天气不错,适合学习");}public abstract void method();//定义抽象方法}class Dog extends Animal{public Dog(){super();System.out.println("dog");}public Dog(String name){super(name);}public void show(){System.out.println("今天天气不错,适合郊游");}public void method(){System.out.println("dog method");}}class AbstractDemo2 {public static void main(String[] args) {//创建对象//Animal a = new Animal();Dog d = new Dog();System.out.println(d.getName());Dog d2 = new Dog("小白");System.out.println(d2.getName());d2.show();d2.method();}}
(4)使用:
当一个类继承一个抽象类的时候
要么重写抽象类的所有抽象方法。
要么本身是一个抽象类。
(5)抽象类的注意事项
A:抽象类没有构造方法,那么有什么用?
有,用于子类实例化使用。
B:是否有非抽象方法?如果没有抽象方法类为什么要定义为抽象类?
有,提高代码复用性。
没有抽象方法的抽象类就是为了不让他能创建对象。
C:abstract不能和哪些关键系并存。
private:私有的功能,子类是不能重写的。而abstract是要求子类重写的。
fianl:最终的意思,子类不能重写。而abstract是要求子类重写的。
static:静态的意思,它是跟类相关的。而我们研究的是对象间的关系。
静态的东西,可以通过类名调用,但是,抽象的方法,用类名调用没有实际意义。
修饰关键字:
默认修饰符,private,public --成员变量private,成员方法public
fianl:最终的,可以修饰类,成员变量,成员方法
static:让成员多了一种调用方式。可以修饰成员。
abstract:修饰类,修饰方法,表示是抽象。
组合使用:
一般格式:
权限修饰符+static+final+成员变量/方法
代码示例:
/*老师示例具体事物:基础班老师,就业班老师共性:姓名,年龄,讲课。根据我们学过的面向对象知识,我们就可以如下分析:定义一个老师类,然后,分别让基础班老师和就业班老师继承老师类。如何定义一个老师类呢,就是分析基础班老师和就业班老师的共性内容:老师类:成员变量:姓名,年龄成员方法:讲课 因为每个老师讲课的内容不一样,所以,我们定义为抽象方法。基础班老师:重写讲课方法输出老师的信息。就业班老师:重写讲课方法输出老师的信息。*/abstract class Teacher{private String name;private int age;public Teacher(){}public Teacher(String name,int age){this.name = name;this.age = age;}public String getName(){return name;}public int getAge(){return age;}//抽象的讲课方法public abstract void teach();public void printMessage(){System.out.println(name+"***"+age);}}class BaseTeacher extends Teacher{public BaseTeacher(String name,int age){super(name,age);}public void teach(){System.out.println("基础班老师讲JavaSE");}/*public void printMessage(){System.out.println(getName()+"***"+getAge());}*/}class WorkTeacher extends Teacher{public WorkTeacher(String name,int age){super(name,age);}public void teach(){System.out.println("就业班老师讲JavaEE");}}class TeacherDemo {public static void main(String[] args) {BaseTeacher bt = new BaseTeacher("林青霞",25);bt.teach();bt.printMessage();WorkTeacher wt = new WorkTeacher("郭德纲",38);wt.teach();wt.printMessage();//使用多态Teacher t = new BaseTeacher("刘姐",18);t.teach();t.printMessage();t = new WorkTeacher("芙蓉姐姐",20);t.teach();t.printMessage();}}
二、接口
(1)接口:当一个抽象类中的方法都是抽象的时候,(并且都是成员常量的时候的。)java提供了一个新的表示形式,那就是接口。
(2)好处:
A:接口是对外暴露的规则(比如:USB,电脑内部的插槽,CPU的针孔)
B:接口是功能的扩展
C:接口降低了程序的耦合性
低耦合:类与类之间的关系
高内聚:类本身的能力
D:接口可以用来多实现
E:类与接口之间是实现关系,而且类可以继承一个类的同时实现多个接口
F:接口与接口之间可以有继承关系
(3)成员特点:
A:成员变量
成员变量都是常量,因为有默认修饰符:public static final
B:成员方法
成员方法都是抽象的,因为有默认修饰符:public abstract
建议,每次自己写接口的时候,尽量把修饰符自己写上。
(4)类,接口相互间的关系:
A:类与类
继承关系,java只支持类的单继承,但是可以多重(层)继承。
B:类与接口
实现关系,可以单实现,也可以多实现。
还可以在继承一个类的同时,实现多个接口。
C:接口与接口
继承关系,可以单继承,也可以多继承。
如果一个类实现一个接口,就必须实现该接口及其父接口的所有抽象方法。
代码示例:
interface Inter//定义一个接口{public abstract void show();//方法是抽象的}interface Inter2//定义第二个接口,两个方法都是抽象的{public abstract void method();public abstract void show();}interface Inter3 extends Inter,Inter2//第三个接口继承了前两个接口{public abstract void function();}class Fu //默认有个extends Object{}class Demo extends Fu implements Inter,Inter2//继承Fu类并实现了前两个接口{public void show()//复写show方法{System.out.println("demo show");}public void method()//复写method方法{System.out.println("demo method");}}
三、抽象类和接口的区别:
(A)成员区别:
抽象类:
构造方法
成员变量:可以是变量,也可以是常量。
成员方法:可以是抽象方法,也可以是非抽象方法。
接口:
成员变量:只能是常量。默认修饰符:public static final
成员方法:只能是抽象方法。默认修饰符:public abstract
(2)类只能单继承
而接口可以多继承。接口的出现避免了java的单继承的局限性。
(3)抽象类被继承,类中定义的是继承体系的共性内容。
接口被实现,接口中定义的是体系的扩展内容。
(4)设计理解不同:
抽象类被继承,体现的是一种:"is a"的关系
接口被实现,体现的是一种:"like a"的关系
代码示例:
abstract class Person//抽象类{private String name;private int age;public void setName(String name){this.name = name;}public String getName(){return name;}public void setAge(int age){this.age = age;}public int getAge(){return age;}public abstract void eat();//定义抽象方法}abstract class Player extends Person{public abstract void study();//抽象方法 }abstract class Coach extends Person{public abstract void teach();//抽象方法}interface StudyEnglish//接口{public abstract void studyEnglish();//接口中的抽象方法}class PingPongStu extends Player implements StudyEnglish{public void studyEnglish()//复写抽象方法{System.out.println("乒乓运动员学英语");}public void study()//复写抽象方法{System.out.println("乒乓运动员学习乒乓");}public void eat()//复写抽象方法{System.out.println("乒乓运动员吃乒乓");}}class PingPongCoach extends Coach implements StudyEnglish{public void studyEnglish()//复写抽象方法{System.out.println("乒乓教练学英语");}public void teach()//复写抽象方法{System.out.println("乒乓教练教学员学乒乓");}public void eat()//复写抽象方法{System.out.println("乒乓教练吃乒乓乒乓");}}class BasketStu extends Player {public void study()//复写抽象方法{System.out.println("篮球运动员学打篮球");}public void eat()//复写抽象方法{System.out.println("篮球运动员吃篮球");}}class BasketCoach extends Coach {public void teach()//复写抽象方法{System.out.println("篮球教练教学员学打篮球");}public void eat()//复写抽象方法{System.out.println("篮球教练吃篮球");}}class PersonDemo{public static void main(String[] args){PingPongStu pps = new PingPongStu();pps.setName("王浩");pps.setAge(44);System.out.println("姓名是:"+pps.getName()+",年龄是:"+pps.getAge());pps.study();pps.eat();pps.studyEnglish();System.out.println("************************");BasketStu bs = new BasketStu();bs.setName("姚明");bs.setAge(50);System.out.println("姓名是:"+bs.getName()+",年龄是:"+bs.getAge());bs.study();bs.eat();System.out.println("************************");PingPongCoach ppc = new PingPongCoach();ppc.setName("乒乓刘教练");ppc.setAge(36);System.out.println("姓名是:"+ppc.getName()+",年龄是:"+ppc.getAge());ppc.teach();ppc.eat();ppc.studyEnglish();System.out.println("************************");BasketCoach bc = new BasketCoach();bc.setName("篮球张教练");bc.setAge(25);System.out.println("姓名是:"+bc.getName()+",年龄是:"+bc.getAge());bc.teach();bc.eat();}}
四、Object类的使用
Object:类Object是类层次结构的根类。每个类都使用Object作为超类。
Object类中我们要掌握的功能:
A:public String toString()
返回该对象的字符串表示。建议所有子类都重写此方法。
如果没有重写,默认的结果是:
getClass().getName() + '@' + Integer.toHexString(hashCode())
类名@哈希值的十六进制
public static String toHexString(int i):把i按照十六进制的数据返回。
为什么要重写呢?
因为地址值的显示对我们来说,没有意义。
为了让显示的效果有意义一些,重写此方法。
代码示例:
class Student extends Object{private String name;public Student(){}public void setName(String name){this.name = name;}public String getName(){return name;}//重写方法public String toString(){//成员变量的组成:多个成员变量用,隔开。//"name:"+name+",age:"+age;return "name:"+name;}}class ObjectDemo{public static void main(String[] args){//创建对象Student s = new Student();s.setName("林青霞");//Student@3e0ebb//其实在用输出语句输出一个对象的名称的时候,其实是用对象调用了toString()方法而已。System.out.println(s);System.out.println(s.toString()); //类@十六进制的hashCode()//hashCode方法System.out.println(s.hashCode()); //4067003 -- intSystem.out.println(Integer.toHexString(4067003)); //3e0ebb}}B:public int hashCode()返回该对象的哈希码值。C:finalize()当垃圾回收器确定不存在对该对象的更多引用时,由对象的垃圾回收器调用此方法。D:Class getClass():反射的时候讲。返回的是该类的字节码文件对象的类文件。E:public boolean equals(Object obj)指示其他某个对象是否与此对象"相等"。 如果类没有重写equals方法,那么它比的还是地址值。 代码示例: class Student{private String name;private int age;public Student(){}public Student(String name,int age){this.name = name;this.age = age;}//重写equals方法public boolean equals(Object obj)//重写的是Object类中的equals方法{//为了提高程序的效率if(this == obj){return true;}//为了提高程序健壮性if(!(obj instanceof Student)){return false;}Student s = (Student)obj; //向下转型//这个if语句可以使用三元运算符改进//下边equals是String类中重写Object类中equals之后的 return this.name.equals(s.name) && this.age == s.age;}}class Demo{}class ObjectDemo3 {public static void main(String[] args) {Student s1 = new Student("李建峰",18);Student s2 = new Student("李建峰",18);Student s3 = new Student("张学友",20);System.out.println(s1.equals(s2));System.out.println(s1.equals(s3));//自己跟自己比System.out.println(s1.equals(s1));Demo d = new Demo();//ClassCastExceptionSystem.out.println(s1.equals(d));}}
五、内部类
1、内部类定义:
将一个类定义在另一个类的里面,对里面那个类就称为内部类(内置类,嵌套类)。
2、访问特点:
A:内部类可以直接访问外部类中的成员,包括私有成员
B:外部类要访问内部类中的成员必须要建立内部类的对象
代码示例:
class Outer{private int num = 10;//成员内部类class Inner{public void show(){System.out.println("num:"+num);}}//成员方法public void method(){//创建对象Inner in = new Inner();in.show();}}class InnerDemo{public static void main(String[] args){//在外部使用Outer o = new Outer();o.method();//注意格式:外部类.内部类 名字 = 外部类对象.内部类对象Outer.Inner oi = new Outer().new Inner();oi.show();}}
3、内部类位置
A:成员位置
a:如果没有被private或者static修饰。
外部类.内部类 名字 =外部类对象.内部类对象;
举例:
Outer.Inner oi = new Outer().new Inner();
oi.show();
b:被private或者static修饰。
如果被private修饰后,就不能再在除了外部类的其他类中使用。
如果被static修饰,并且没有被private修饰,使用方式如下:
外部类.内部类 名字 =外部类.内部类对象;
举例:
Outer.Inner oi = new Outer.Inner();
oi.show();
代码示例:
/*内部类被静态修饰:*/class Outer{private static int num = 10;static class Inner{public void show(){System.out.println("show:"+num);}public static void method(){System.out.println("method:"+num);}}}class InnerDemo3 {public static void main(String[] args) {//Outer.Inner oi = new Outer().new Inner();Outer.Inner oi = new Outer.Inner();oi.show();oi.method();//静态的不想通过对象访问Outer.Inner.method();}}
内部类被private修饰:
/* 内部类被private修饰*/class Outer{private int num = 10;private class Inner{public void show(){System.out.println("num:"+num);}}public void method(){Inner in = new Inner();in.show();}}class InnerDemo2 {public static void main(String[] args) {//内部类被private修饰后就不能再被使用//Outer.Inner oi = new Outer().new Inner();Outer o = new Outer();o.method();}}
B:局部位置
a:有名字
按照普通的方式使用即可。
b:没有名字,匿名内部类(掌握)
格式:
new 类或者接口()
{
重写方法,或者自定义方法
};
其实这里的本质是一个子类匿名对象。
前提:外部存在着一个类或者接口。
内部类定义在局部位置:
在外部类的方法中定义一个类。
为什么局部内部类访问局部变量需要用final修饰呢?
因为内部类在使用完毕后,可能在堆内存还存在呢,这个时候,它要的变量也要存在。
如果没用final修饰,变量就会从栈中消失。
final修饰的内容在哪里?
方法区里面有一个常量区。它的生命周期你可以想象成和static一样。
代码示例:
class Outer{//private int num = 10;public void method(){final int num = 20;//局部位置class Inner{public void show(){System.out.println("show "+num);}}//创建对象Inner in = new Inner();in.show();}}class InnerDemo4 {public static void main(String[] args) {Outer o = new Outer();o.method();}}
什么时候使用匿名内部类呢?
通常在使用方法是接口类型参数,并该接口中的方法不超过三个时,可以将匿名内部类作为参数传递。
增强阅读性。
匿名内部类的使用:
interface Inter{public abstract void hello();public abstract void haha();}class Outer{private int num = 10;public void method(){/*class Inner//内部类形式{public void show(){System.out.println("num:"+num);}}Inner in = new Inner();in.show();*//*new Inter(){//匿名内部类public void hello(){System.out.println("hello");}};*///怎么调用呢?/*new Inter(){//匿名内部类调用方法public void hello(){System.out.println("hello");}}.hello();*//*new Inter(){public void hello(){System.out.println("hello");}public void haha(){System.out.println("haha");}}.hello();new Inter(){public void hello(){System.out.println("hello");}public void haha(){System.out.println("haha");}}.haha();*///假如只是实现了接口的方法,那么还可以这样用Inter in = new Inter(){public void hello(){System.out.println("hello");}public void haha(){System.out.println("haha");}};in.hello();in.haha();}}class NiMingInnerDemo {public static void main(String[] args) {Outer o = new Outer();o.method();}}
- 黑马程序员java学习日记——面向对象(三)
- 黑马程序员--【学习日记三】——java面向对象(一)
- 黑马程序员--学习日记(三)面向对象基础
- 黑马程序员学习日记 (三)面向对象
- 黑马程序员-iOS学习日记(三)面向对象-方法
- 黑马程序员java学习日记——面向对象(二)
- 黑马程序员--【学习日记四】——java面向对象(二)
- 黑马程序员Java学习日记(2)面向对象
- 黑马程序员——(学习日记——面向对象)面向对象常见对象
- 黑马程序员学习日记——面向对象-封装
- 黑马程序员——学习日记之--面向对象总结
- 黑马程序员——学习日记之面向对象基础
- 黑马程序员——学习日记之面向对象特征
- 黑马程序员——Java面向对象(三)
- 黑马程序员——Java面向对象知识点(三)
- 黑马程序员——JAVA 面向对象总结(三)
- 黑马程序员——Java基础-------面向对象(三)
- 黑马程序员————学习日记【5】 【Java面向对象1】
- 怎样比较两个集合是否相等
- java集合源代码分析(一)
- iOS 如何在一个应用程序中调用另一个应用程序
- hibernate 正向和反向工程
- hdu1325Is It A Tree?【并差集】
- 黑马程序员java学习日记——面向对象(三)
- cocos2d-x 2.x action动作整理集合
- 白话 __vm_enough_memory,检查内存是否充足
- 数学中求各种多边形的面积
- Ubuntu 12.04安装QQ2012,下载后请根据自己的机器类型,按照下面的32位或64位安装说明安装
- 关闭chrome 中flash
- 第十一堂课后作业
- 一台 DHCP 多个不同VLAN分配IP地址
- 三大框架整合 提示 不能进行查询错误