面向对象
1.面向对象(D10)
1.
car c=new car();
对象也是引用型变量,存储在堆内存中,c是引用型变量,存储的是car的内存地址,c:car类型的对象
2.
类是对一类事物的抽象描述,是对象的模板,对象用于表示现实中该类事物的个体。
3.
成员变量有默认初始值
null,0, 0.0
局部变量没有默认初始值,不赋值不能使用
4.
成员变量跟随对象进入堆内存存储
局部变量跟随方法进入栈存储
5.
面向对象有三大特征
封装,继承,多态
6.
private属于成员修饰符,不能修饰局部变量
加上private关键字,只能在本类中初始化,外部类无法直接访问,因此可以通过本类中设计set()函数进行方法赋值,set()函数内可以加入条件判断
7.
类中的属性都私有化,但是需要提供get()和set()函数,进行间接访问
8.
方法中,有this.的访问的是成员变量,哪个对象调用包含this,this就表示哪个对象
9.
java中不允许多继承,但可以多重继承(多层继承)
10.
用子类的对象调用成员变量,子类自己有就使用自己的,子类没有就调用父类的(就近原则)
11.
子类出现和父类一模一样的方法时,子类对父类的方法进行重写(override)
12.
子类方法覆盖父类方法,必须保证子类的权限大于等于父类的权限
13.
四大权限
public protected default private
14.
抽象类,不能实例化对象,因为抽象方法没有主体,无法运行,抽象方法一定要定义在抽象类中
public abstract class develop{
public abstract void work();//不写大括号
}
定义类继承抽象方法,将抽象方法进行重写,创建子类对象
抽象类的作用,保证继承的体系的完整性,强制子类重写抽象的方法,
abstract无法和private, final static一起使用,产生矛盾
15.
抽象类可以没有抽象方法,意义在于:不会让其他人直接创建该类对象,作为中间层
1.接口(D11)
1.接口只描述应该具备的方法,并没有具体实现,具体实现由接口的实现类来完成(相当于接口的子类),定义与实现分离
2.类与接口的关系为实现关系,使用implements关键字,定义类,实现接口,重写接口中的抽象方法,类实现接口,可以理解为继承
类名 实现 接口名
public class MyInterfaceImpl implements MyInterface{
}
没有变量,都是常量
常量定义:public static final 数据类型 变量名=10;SF
成员方法定义:public abstract 返回值 方法名字(参数列表);A
3.static可以被类名或者接口名+(点)直接调用
4.子类(实现类)必须覆盖接口所有的抽象方法之后,才能实例化,否则,子类就是一个抽象类
5.接口的意义:解决了多继承的弊端,通过多实现完成
6.多实现消除了多继承的安全隐患,因为接口中的方法都是抽象的没有主体,需要依赖类的重写才能实现
7.抽象类是体系应该有的功能,接口是体系特殊功能
eg 犬 行为(吼叫,吃饭)
缉毒犬 行为(吼叫,吃饭)缉毒(接口定义)
1.多态(D11-12)
1.类person,students
students extends person{}
public static void(String [] args){
students s =new student();
person p=new student();
p.方法() 运行的是子类的重写方法
}
接口 变量名=new 实现类();
父类 变量名=new 子类();
最终多态体现为,父类的引用变量指向子类对象,同样适用于抽象类
在使用多态后的父类引用变量调用方法时,会调用子类重写后的方法
多态的三种调用方法,普通类,抽象类,接口
1.public class Fu{
class Zi extends Fu{}
2.public abstact class Fu{}
class Zi extends Fu{}
3.pulic interface Fu{}
class Zi implements Fu{}
2.成员特点
1.成员变量(编译,运行看父类)
编译时,参考父类中有没有这个变量,如果有,编译成功,没有,编译失败。
运行时,运行的是父类中的方法值。
2.成员方法(编译看父类,运行看子类)
编译时,参考父类中有没有这个方法,如果有,编译成功,没有,编译失败。
运行时,运行的是子类重写的方法,如果子类没有重写,运行父类的方法。
PS.静态时(编译,运行看父类)
成员变量:编译运行全是父类
成员方法:编译时,参考父类中有没有这个方法,如果有,编译成功,没有,编译失败。
运行时,运行的是父类中的方法值。
3.instanceof关键字(对于有继承关系或者实现关系的类)
1.person p=new student();
person p=new teacher();
boolean b=p instanceof teacher; //p是否是teacher类型的对象变量
4.向下转型
原因:多态可以调用子类和父类的公有方法,但是无法调用子类的特有方法,所以使用向下转型
1父类类型强制转换为子类类型,好处,调用子类中特有的功能
Fu f=new Zi();
Zi z=(Zi)f ;
1.构造方法(D12)
main方法先入栈,开始执行,在堆内存中建立new person区域,赋默认值,new person调用构造方法,构造方法入栈,将参数“张三”,20传递给构造器,this语句对堆内存初始化,之后将内存地址0x001传递给对象变量P
2.this在构造器之间的调用
public person(){ //无参构造器
this("张三",19); //调用有参数的构造器,该语句需要写在构造器的第一行
}
public person(String name.int age){
this.name=name;
this.age=age;
}
3.super关键字
1.super
子类中使用super()调用父类的构造方法,将super()直接看做函数,有参super()直接将参数传递给父类的构造器,对变量进行赋值。
super()调用父类的无参构造器
super(xxx)调用父类的有参构造器
2.D12-13
new 类的时候,自动调用构造器
子类有一个默认添加的构造方法,子类构造方法的第一行有一个隐式的代码suer(),
public student(){
super(); //调用父类的无参数构造方法
}
3.super代表了父类在内存中的位置
4.Attention
public class person{
public person(int a){
}
}
public class students extends person{ //报错,父类没有无参构造器
public student{
super();
}
}
D13
1.final修饰类,除了该类不能被继承之外,其余用法都相同。
public final class student{
}
2.final修饰方法,不能被重写。
public final void show(){
}
3.final修饰成员变量,固定的不是内存的默认值,固定的是手动的赋值。
final int age=1 final int age=0//0是赋值,和内存默认值意义不同
4.final修饰引用形变量,变量的内存地址将终身不变
final Zi z=new Zi();
z=0x4de,终身不变
5.成员变量的赋值,定义的时候直接赋值,或者使用构造方法
final int age=1 ;
或者
final int age;
public person(int age){
this.age=age;
}
成员变量需要在创建对象前赋值,否则报错,即只能直接赋值,或者构造器赋值,不能使用set方法赋值,因为构造器赋值在new对象的时候已经完成
6.Static修饰共享属性,减少浪费
public class person{
private String name;
static String className;
}
person p1=new person();
person p2=new person();
p1.className="基础班";
System.out.println(p2.className)//同样为基础班
7.被static修饰的成员可以被类名直接调用
System.out.println(person.className)
8.类进入到方法区,先把静态属性或者方法加载到静态区,作为共享
类进入方法区后先加载自己的静态成员到静态区,静态属于类,即main属于test,className属于person,静态成员有默认值,null,开始执行后JVM将main复制一份压栈执行,JVM到静态区,找到属于person类的静态属性,className,打印出null,静态优先于非静态存在。
9.static的注意事项
在静态中不能调用非静态
static优先于非静态存在于内存中 ,所以不能使用this/super
10.static的应用场景
成员变量:是否有共性属性
成员方法:跟着变量走,如果调用了静态变量,则方法就加static,调用了非静态变量,方法不能加static
没有使用成员变量,就使用static,否则需要浪费一个对象才能调用。因为不加static的调用时需要new对象,加static的方法直接可以用
类名.方法名调用
11.定义静态常量
Public static final String COMPANY-NAME="itcast"; 变量名大写,多个单词用下划线连接
12.匿名对象
只能使用一次,可以作为方法的参数进行传递,减少代码量
~public void method (person p); method (new person);
~public person method (){
return new person();
}
13.权限修饰符
int i=1; 即默认权限(default),仅在本包下可以使用,如果2类继承1类,两者不在一个包内,且导入1的包,无法使用,因为不在一个包下。
protected权限:本包中的类和其他包的子类调用,且只能是子类的里面,直接调用。
public class A{
protected void abc(){
sop("abc");
}
}
public class B extends A{
abc();
}
14.代码块
静态代码块,无论new几次,只执行一次 static{}
构造代码块,new一次,执行一次 {}
构造方法,new一次,执行一次
1.类作为参数( D14 )
public person{
public void show{
sop("show方法执行");
}
}
public static void main(String args [] ){
person p=new person();
method(p);
public void method(person p){
p.show();
}
}
2.抽象类作为参数
体现多态调用的扩展性
public abstract class Animal {
public abstaract void ear();
}
pubic class cat extends Animal {
sop("吃鱼");
}
public static void main(String args [] ){
cat c=new cat();
operatorAnimal(c);
public static void operatorAnimal(Animal a ) {//由于是抽象类,没有对象,只能调用Animal的子类对象
a.eat(); //execute super class Animal's function
}
}
3.抽象类作为返回值
public class getAnimal(){
public Animal getAnimal(){
if(i==0)
return new cat(); //返回cat,类型是Animal
return new dog();
}
}
public static void main(String args [] ){
getAnimal g=new getAnimal();
Animal a = g.getAnimal(0); //需要用父类(或者接口)接收,不能写死
Animal a = g.getAnimal(1);
}