重识Java第六天打卡----面向对象进阶2【包、权限修饰符、final和static,关键字、常量、枚举、抽象类、多态】

活动地址:CSDN21天学习挑战赛

一、包和权限修饰符

1.什么是包?

包是一种划分类的层次和结构的封装形式,类似于文件管理系统中的文件夹,并且实际也是以文件夹为形式载体的

2.包的作用

  • 对类文件进行分类管理。
  • 给类文件提供多层名称空间。

3.包的一般规则及导包

(1)一般规则

  • 建包语句必须在第一行;
  • 一般在定义包名时,因为包的出现是为了区分重名的类。所以包名要尽量唯一。(可以使用url域名来进行包名称的定义,且域名要倒置,如 package com.windx.javabean;)
  • 包的名称建议全部小写;
  • 若生成的包不在当前目录下,最好要执行classpath,将包所在父目录定义到classpath变量中;

(2)导包

  • 相同包下的类可以直接访问,不同包下的类必须导包,才可以使用!
  • 当一个类中需要用到不同包中名称相同的不同类时,默认只能导入一个类,另一个类要带包名访问。【这种情况一定要注意不要导错了包!
  • 导包格式:import 包名.类名;

4.权限修饰符

由于包与权限修饰符有一定关,所以就在一起说

(1)分类及具体作用范围

权限修饰符:有四种作用范围由小到大
private --> 缺省 --> protected --> public
具体如下:

修饰符同一 个类中同一个包中其他类不同包下的子类不同包下的无关类
private
缺省
protected
public

(2)如何使用权限修饰符?

  • 成员变量一般私有。
  • 方法一般公开
  • 若只希望本类访问,则使用private
  • 如果只希望本类,同一个包下的其他类和子类访问,使用protected修饰

二、final关键字和static关键字

1.final关键字

(1)基本解释

final 关键字是最终的意思,可以修饰(类、方法、变量)

(2)作用

final关键字的作用

(3)注意事项

  • final修饰的变量一定要初始化
  • final修饰的变量是基本类型:那么变量存储的数据值不能发生改变。
  • final修饰的变量是引用类型:那么变量存储的地址值不能发生改变,但是地址指向的对象内容是可以发生变化的。
  • (如修饰一个实例对象时,可以改变实例对象的属性,但是不能改变该对象名的地址指向)

2.static关键字

(1)基本解释

static方法一般称作静态方法,被其修饰的方法或变量不再需要使用对象进行访问,因此方便在没有创建对象的情况下来进行调用方法/使用变量。

(2)注意点

  • static修饰的变量不需要初始化,会有默认赋值
  • 由于静态方法/变量不依赖于任何对象就可以进行访问,因此它们没有this可以使用
  • 静态方法不能访问类的非静态成员变量非静态成员方法,因为非静态成员方法/变量都是必须依赖具体的对象才能够被调用。

具体例子(下图红色为idea中提示错误语法):
static关键字演示

下面是具体代码,大家也可以自己进行试验

public class Test2 {
    private static String str1 = "windx";
    private String str2 = "xlk";

    private void print0(){
        System.out.println("私有静态方法");
    }

    public Test2(){}

    //非静态方法---可以调用静态的,也可以调用非静态的
    public void print1(){
        System.out.println(str1);
        System.out.println(str2);
        print0();
    }

    //静态方法---不可以使用非静态变量和非静态方法
    public static void print2(){
        System.out.println(str1);
        System.out.println(str2);
        print0();
    }
}

其他static详细作用见笔者上一章博文

3.常量

(1)基本解释

常量 是使用了public static final修饰的成员变量,必须有初始化值,而且执行的过程中其值不能被改变。

(2)使用场景及规范

使用场景

由于其本质就是进行字面量的替换,即 在编译阶段会进行“宏替换”:把使用常量的地方全部替换成真实的字面量
所以常常使用在一些常用固定数值上,如

  • JavaGUI很多程序的长宽设置
  • 计算简单数学题时,确定π的近似值
  • 一些常用字符串等等

使用规范

  1. 使用大写的英文字母,若有多个则用下划线连接,如 PASS_WORD
  2. 一般定义在类的开头位置

三、枚举

1.基本解释

简单说下注意事项,平时我用的不多
枚举是一种特殊的类型,大概也算引用类型吧,跟String性质差不多

2.枚举的使用

格式:
修饰符 enum 枚举名称{
第一行都是罗列枚举类实例的名称。
}
一般修饰符常常省略,例子如下:

enum Season{
   SPRING , SUMMER , AUTUMN , WINTER;
}

3.深入了解枚举

反编译后的枚举
枚举的特征如下
在这里插入图片描述

四、抽象类

1.基本解释

使用abstract关键字修饰类,这个类就是抽象类;修饰方法,这个方法就是抽象方法。

2.使用规范

格式:抽象类
抽象方法

3.注意事项

  • 抽象方法只有方法签名,不能声明方法体。
  • 一个类中如果定义了抽象方法,这个类必须声明成抽象类,否则报错。
  • 抽象类不一定有抽象方法,但是有抽象方法一定是抽象类!
  • 抽象类的作用就是提取公共部分,然后作为父类,让具体类来继承的
  • 抽象类不可以创建实例对象,因为其构造器是私有的
  • 有种跟final作对的感觉,hhh

五、面向对象三大特性之三 ---- 多态

1.什么是多态

多态指的是 对象可以有多种形态

2.多态的前提

  • 有继承/实现关系;
  • 有父类引用指向子类对象;
  • 有方法重写(多态侧重行为多态

3.类型转换(代码讲解)

public class Test {
    public static class Animal{
        private String name;
        Animal(){
            System.out.println("父类的空构造器");
        }
        Animal(String name){
            this.name = name;
            System.out.println("父类带参构造");
        }
        public void eat(){
            System.out.println("吃东西");
        }

        public String getName() {
            System.out.println("我是一只小动物,我的名字叫"+this.name);
            return name;
        }

        public void setName(String name) {
            this.name = name;
        }
    }

    public static class Cat extends Animal{
        private String name;
        Cat(){
            System.out.println("子类的空构造器");
        }
        Cat(String name){
            this.name = name;
            System.out.println("子类带参构造");
        }

        @Override
        public void eat() {
//            super.eat();
            System.out.println("小猫吃鱼");
        }

        public void play(){
            System.out.println("小猫玩逗猫棒");
        }

        @Override
        public String getName() {
            System.out.println("我是一只小猫,我的名字叫"+this.name);
            return name;
        }
    }


    public static void main(String[] args) {
        Cat c1 = new Cat();
        System.out.println("-------");

        Animal c2 = new Cat("加菲");  //从子到父,自动类型转换
        c2.eat();  //只可以调用父类有的方法,若子类有重写,则调用重写方法
        c2.getName();
//        c2.play();  //若是子类独有的方法,则无法调用
        System.out.println("-------");

        Animal c3 = new Animal();  //从父到子,强制类型转换
        //强制转换原则----java中父类强制转换成子类的原则:父类型的引用指向的是哪个子类的实例,就能转换成哪个子类的引用。
        c3.eat();
        if (c3 instanceof Cat){
            Cat c4 =(Cat)c3;  //这里报错,说c3 is Null,奇怪
            c4.eat();
            c4.play();
        }else {
            System.out.println("c3不是Cat类的实例,所以不能强制转换");
        }

        Cat c5 = (Cat) c2;  //本来c2是不能调用子类方法的,但是强转为Cat类后就可以了
        c5.play();
        c5.getName();


    }
}

上述代码实现结果如下:
在这里插入图片描述
由此可见,在Java中有以下两种类型转换

  1. 自动类型转换(从子到父)
    无法调用子类独有的方法和变量
  2. 强制类型转换(从父到子)
    原则:父类型的引用指向的是哪个子类的实例,就能转换成哪个子类的引用。

强制转换前可做一个条件判断,如下:

 if (c3 instanceof Cat){
            Cat c4 =(Cat)c3;  //这里报错,说c3 is Null,奇怪
            c4.eat();
            c4.play();
        }else {
            System.out.println("c3不是Cat类的实例,所以不能强制转换");
        }

后面还会进一步探讨强制转换的问题~大家也可以在评论区留下你的看法,一起进步!

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值