欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

JavaSE---01类与对象

程序员文章站 2022-04-05 19:42:54
...

1 POP与OOP

POP:面向过程
OOP:面向对象

POP与OOP都是一种思想,面向对象是相对于面向过程而言的。面向过程强调的是功能行为、以函数为最小单位,考虑怎么做。面向对象将功能封装进对象,强调具备了功能的对象,以类/对象为最小单位,考虑谁来做

2 面向对象特性

  • 封装
    把客观事物封装成抽象的类,并且类可以把自己的数据和方法只让可信的类或者对象操作,对不可信的进行信息隐藏。
  • 继承
    继承是一个对象获得另一个对象的属性的过程。就像是我们现实生活中的父子关系,儿子可以遗传父亲的一些特性,在面向对象语言中,就是一个类可以继承另一个类的一些特性,从而可以代码重用,其实继承体现的是is-a关系,父类和子类在本质上还是一类实体。
    继承的特征:
      1、可传递可扩展,若类C继承类B,类B继承类A(多继承)则类C既有从类B那里继承下来的属性与方法,也有从类A那里继承下来的属性与方法,还可以有自己新定义的属性和方法
      2、可复用,若类B继承类A,那么建立类B时只需要再描述与基类(类A)不同的少量特征(数据成员和成员方法)即可。这种做法能减小代码和数据的冗余度,大大增加程序的重用性。
      3、可维护性。继承通过增强一致性来减少模块间的接口和界面,大大增加了程序的易维护性。

科普:IS-A、IS-LIKE-A、HAS-A和USE-A都是用来便是类与类之间的关系
简单点就是:

  • 如果继承过程中,仅仅是覆盖了父类中的方法,那就是IS-A关系;如果有新增的方法,则为IS-LIKE-A关系。
  • 类B中的属性有类A,那就是HAS-A关系
  • 类B中有关方法使用类A做为形参,这就是USA-A关系:例如 public void test(A a)
  • 多态
    多态就是同一个接口,使用不同的实例而执行不同操作
    如果类A与类B是IS-A关系,那么就是 B is-a A ,A继承B,可以写成 A a = new B()

3 类与对象

  • 类:是一个模板,它描述一类对象的行为和状态
  • 对象[实例]:是类的一个实例(对象不是找个女朋友),有状态和行为。例如,一条狗是一个对象,它的状态有:颜色、名字、品种;行为有:摇尾巴、叫、吃等。

3.1 类与对象的创建

public class Dog{//模板,所有狗的共性
  //属性
  String breed;
  int age;
  String color;
  //方法
  void barking(){
  }
 
  void hungry(){
  }
 
  void sleeping(){
  }
}

public static void main(String[] args){
	//创建一个狗的实例(对象)
	Dog dog = new Dog();
}

3.2 对象的创建分析

这里涉及了一点String常量池跟JVM知识点。不过只要你创建对象时使用关键字new那么这个对象是在堆里面生成的,变量引用堆中的地址
JavaSE---01类与对象

4 访问修饰符

成员变量有四种修饰符

  • private 私有的
  • default 默认不写
  • protected 受保护的
  • public 公共的
修饰符 当前类 同一包内 子孙类(同一包) 子孙类(不同包) 其他包
public Y Y Y Y Y
protected Y Y Y Y/N Y
default Y Y Y N N
private Y N N N N

对于除protected的其他访问权限可以很好理解:
1. public:在所有包中所有类中都可见
2. default :只能在同一个包下的类里面可见
3. private :只能在当前类中可见,不能修饰外部类

4.1 protected修饰符

对于protected修饰符要从两个方面分析:

1.子类与基类在同一包中:被声明为 protected 的变量、方法和构造器能被同一个包中的任何其他类访问;
2.子类与基类不在同一包中:那么在子类中,子类实例可以访问其从基类继承而来的 protected 方法,而基类实例不能访问protected方法。
第2句的理解为下面的代码:

package p1;
public class Father1 {
    protected void f() {}    // 父类Father1中的protected方法
}

package p11;
import p1.Father1;
public class Son11 extends Father1 {
    public static void main(String[] args) {
        new Son11().f();
        //new Father1().f();不能访问
    }
}

4.2 protected修饰判断可见的规则

1.看访问的protected修饰的在哪个包下,那么这个包下所有类都能访问。
2.如果不在一个包下,看这个类是不是protected所在类的子类,如果是那么在这个类里,这个类的实例可以访问protected方法,但是这个类的父类实例不能访问【看不懂就看上面的2子类与基类不在同一包中】,如果不是子类,那么访问不了

5 static关键字

5.1 静态属性

  • 当一个属性被static修饰的时候就叫做类属性,又叫做静态属性
  • 当一个属性被声明成类属性,那么所有的对象,都共享一个值
  • 与对象属性对比:
    • 不同对象的 对象属性 的值都可能不一样。比如同学A与同学B的身高不同。
    • 但是所有对象的类属性的值,都是一样的。比如同学A跟同学B都要考试。
  • 访问类属性有两种方式:
    • 对象.类属性
    • 类.类属性(推荐)

5.2 静态方法

  • 当一个方法被static修饰的时候就叫做类方法 ,又叫做静态方法
  • 对象方法: 又叫实例方法,非静态方法
  • 与对象属性对比:
    • 访问一个对象方法,必须建立在有一个对象的前提的基础上
    • 访问类方法,不需要对象的存在,直接就访问
  • 调用类方法
    • 对象.类方法;
    • 类.类方法(推荐)

6 属性的初始化

6.1 对象属性初始化

对象属性初始化有3种【三种都有按照1,2,3的顺序执行】

  1. 声明该属性的时候初始化
  2. 初始化块
  3. 构造方法中初始化
	public String name = "some hero"; //声明该属性的时候初始化
    protected float hp;
    float maxHP;
     
    {
        maxHP = 200; //初始化块
    }  
     
    public Hero(){
        hp = 100; //构造方法中初始化
         
    }

优先级:1>2>3

6.2 类属性初始化

类属性初始化有2种【两种都有按照1,2顺序执行】

  1. 声明该属性的时候初始化
  2. 静态初始化块
	public String name;
    protected float hp;
    float maxHP;
     
    //物品栏的容量
    public static int itemCapacity=8; //声明的时候 初始化
     
    static{
        itemCapacity = 6;//静态初始化块 初始化
    }
     
    public Hero(){
       
    }
     
    public static void main(String[] args) {
        System.out.println(Hero.itemCapacity);
    }

优先级:1>2

7 分析类创建时的执行过程

父类:

public class Father {
    public String name;
    protected float hp;
    float maxHP;

    //物品栏的容量
    public static int father=8; //声明的时候 初始化

    static{
        father = 6;//静态初始化块 初始化
        System.out.println("父类的静态代码块");
    }

    {
        name="父亲";
        System.out.println("父类的构造代码块");
    }
    public Father(){
        System.out.println("父类的构造方法");
    }
}

子类:

public class Son extends Father {
    public String name;
    protected float hp;
    float maxHP;

    //物品栏的容量
    public static int son=8; //声明的时候 初始化

    static{
        son = 6;//静态初始化块 初始化
        System.out.println("子类的静态代码块");
    }
    {
        name="儿子";
        System.out.println("子类的构造代码块");
    }

    public Son(){
        System.out.println("子类的构造方法");
    }

    public static void main(String[] args) {
        Son son = new Son();
    }
}

输出结果:

父类的静态代码块
子类的静态代码块
父类的构造代码块
父类的构造方法
子类的构造代码块
子类的构造方法

执行过程:
当在main方法里面执行new Son()时,先去创建父类的静态属性,创建完成后执行父类的静态代码块,然后去子类创建子类的静态属性,创建完成后执行子类的静态代码块;之后先创建子类的对象属性再去父类创建对象属性,创建完成后执行父类的构造代码块,再执行父类的构造方法;之后执行子类的构造代码块,再执行子类的构造方法