Java基础语法

Java基础语法

内存图

在这里插入图片描述

方法

方法是什么

System.out.println()

类.对象.方法

方法是:1.语句的结合

​ 2.包含于类或对象中

​ 3.在程序中被创建,在其他地方被引用

原则:1个方法做1个功能

命名规则

  • 项目名:随意
  • 包名:小写,域名倒写,单词拼接_(下划线)
  • 类:首字母大写和驼峰原则GoodMan
  • 类成员(成员变量):首字母小写+驼峰原则lastName
  • 局部变量:首字母小写+驼峰原则
  • 方法名:首字母小写+驼峰原则runRun()
  • 常量:大写字母+下划线`MAX_VALUE

方法的定义

1.修饰符 返回值类型 方法名(参数类型 参数名){

方法体

return 返回值

}


2.包含一个方法头和一个方法体
3.

a.修饰符(告诉编译器如何调用此方法,定义了该方法的返回类型)

b.返回值类型 returnValueType是方法返回值的数据类型,无返回值——>其关键字 void

c.方法名 方法的实际名字,方法签名:方法名+参数表

d.参数类型 参数:像占位符,被调用的时,传值给参数

​ 参数列表:方法的参数类型+顺序+参数个数(方法可有可无参数)

​ 形参:接受数据 public static int max(int num)num是形参

​ 实参:被调用时传给方法的数据 int max=max(10)中10是实参

e.方法体 包含具体语句,定义方法的功能


4.方法就像C语言中的函数

方法的调用

  • 调用方法 对象名.方法名(实际参数)
  • Java中是值传递
  • 静态方法(添加一个static)
  • 非静态方法——>要有一个对象来调用
  • 形参和实参
  • 值传递和引用传递(传对象,实质传值)
  • this关键字——调用当前类的方法
public class Student{
public static void say(){
System.out.println("学生");
}
}
public class Demo01{
public static void main(String[]args){
Student.say();
}
}
  • 如果要实例化这个类,要new,对象类型 对象名=对象值;

    Student student=new Student();
    student.say();
    

方法的重载

  • 在一个类中,有相同的函数名称,但形参不同的函数
  • 规则
    • 方法名相同
    • 参数列表不同,个数\类型\参数排列顺序······不同
    • 返回值类型可一样可不一样,不可根据返回值类型判断是否是方法的重载
    • 编译器会根据是否是方法的重载去调用该方法,否则不通过
public class Demo01{
   public static void main(String[]args){
   int max=max(10,10//实参);
   System.out.println(max);
   }
   public static int max(int num1,int num2//形参){
   int result=0;
   if(num1==num2){
   System.out.println("num1=num2");
   return 0;//终止方法
   }
   if(num1>num2){
   result=num1;
   }else{result=num2;}
   return result;
   }
}

命令行传参

  • 传递命令行参数给main()函数实现
  • 在命令行中(通过cmd中输入值)——>在main()函数实现
public static Demo02{
public static void main(String[]args){
  for(int i=0;i<args.length;i++){
  System.out.println("args["+i+"]:"+"args[i]");
  }
}
}

输入 this is a student

args[0]:this
args[1]:is
args[2]:a
args[3]:student

可变参数

  • 传递同类型的可变参数给一个方法
  • 方法声明中:在指定参数类型后加一个省略号(···)
  • 一个方法中只能指定一个可变参数,必须是方法的最后一个参数
public static void main(String[] args) {
        printMax(32,32,99,32,44,45,32);}

public static void printMax(double···numbers){
 if(numbers.length==0){
  System.out.println("No argument passed");
   return;}
     double result=numbers[0];
     for(int i=1;i<numbers.length;i++){
     if(numbers[i]>result){
     result=numbers[i];
     }
     }
     System.out.println("The max value is "+result);//The max value is 99.0
}

递归

  • 少用,递归调用方法会在栈中分配一个空间(叫做栈帧(用于存储该方法的参数、局部变量等)),调用多次,增加空间,会溢出
  • A方法调用A方法
  • 递归结构包括两个部分:
    1. 递归头:什么时候不调用自身方法,如果没有头,将陷入死循环
    2. 递归体:什么时候需要调用自身方法
  public static int f(int n) {
        if (n == 1)
            return 1;
        else {
            return n * f(n - 1);
        }
    }
        public static void main (String[]args){
            System.out.println(f(5));//120
        }
    

数组

数组的声明和创建

声明/定义
  • 类型 []数组名;int[] nums;
  • 类型 数组名[]; int nums[];
创建
  • 数组名=new 数组类型值; nums=new int[10];

    或者声明+创建 int[] nums=new int[10];

  • 给元素赋值

    nums[0]=1;

    nums[1]=2;

  • 数组不赋值默认为0

  • 特点

    1. 长度确定,一旦创建,大小不可变
    2. 相同类型
    3. 数组对象在堆中,属于引用类型,数组本身就是对象,其元素就是对象的成员变量

数组初始化

静态初始化

int[a]={1,2,3};

Man[] mans={new Man(1,1),new Man(2,2)};

动态初始化
int[]a=new int[2];
a[0]=1;
a[1]=2;
默认初始化
  • 数组是引用类型,元素相当于类的实例变量,元素值为0

数组的使用

  • 打印
public class ArrayDemo01 {
    public static void main(String[] args) {
        int[]arrays={1,2,3,4,5};
        //打印数组中的元素
        for(int i=0;i<arrays.length;i++){
            System.out.print(arrays[i]+" ");//1 2 3 4 5 
        }
    }
}
  • 增强打印(for-each循环)
public class ArrayDemo02 {
    public static void main(String[] args) {
        int []arrays={1,2,3,4,5};
        //使用arrays.for直接生成
        //使用增强for循环
        // array是数组中的每个元素
        //适合打印输出,但是取不到下标
        for (int array: arrays) {
            System.out.print(array);
        }
    }
}

  • 使用数组进行排序

Arrays类

  • Arrays.toString(a)(使用工具打印)可以打印出数组内的元素,直接打印出哈希值
public class ArrayDemo03 {
    public static void main(String[] args) {
        int[]a={1,2,3,4,3932,90};
        System.out.println(a);//[I@7c30a502,打印出哈希值
        System.out.println(Arrays.toString(a));//[1, 2, 3, 4, 3932, 90]

    }
}

或者写一个方法打印

public class ArrayDemo03 {
    public static void main(String[] args) {
        int[]a={1,2,3,4,3932,90};
        System.out.println(a);//I@7c30a502,打印出哈希值
        //System.out.println(Arrays.toString(a));
        printArray(a);

    }

    public static void printArray(int[]a) {
        for(int i=0;i<a.length;i++){
            if(i==0){
                System.out.print("[");
            }
            if(i==a.length-1) {
                System.out.print(a[i] + "]");
            }else{
                System.out.print(a[i]+",");
            }
        }
    }
}

  • Arrays类中的方法都是static修饰的静态方法,在使用时可以直接使用类名调用,而“不用”使用对象来调用(不是不能)
  • 功能
  1. 给数组赋值:通过fill方法Arrays.fill(a,0)则数组中的元素都是0
  2. 对数组排序:通过sort方法,按升序Arrays.sort(a)
  3. 比较数组:通过equals方法比较数组中元素值是否相等
  4. 查找数组元素:通过binarySearch方法能对排序好的数组进行二分法查找法操作

冒泡排序

  • 两两选择(相邻)
  • 下一轮少一次排序
import java.util.Arrays;

public class Demo04 {
    public static int[] sort(int[]array) {
        int temp=0;
        for(int i=0;i<array.length;i++){
            for(int j=0;j<array.length-i-1;j++){
                if(array[j+1]<array[j]){
                    temp=array[j];
                    array[j]=array[j+1];
                    array[j+1]=temp;
                }
            }
        }
        return array;
    }

    public static void main(String[] args) {
        int[]a={1,3,45,34,2,42};
        int[] sort=sort(a);
        System.out.println(Arrays.toString(sort));
    }
}

  • 优化减少循环次数 ,注释部分
import java.util.Arrays;

public class Demo04 {
    public static int[] sort(int[]array) {
        int temp=0;
        for(int i=0;i<array.length;i++){
            //boolean flag=false;
            for(int j=0;j<array.length-i-1;j++){
                if(array[j+1]<array[j]){
                    temp=array[j];
                    array[j]=array[j+1];
                    array[j+1]=temp;
                    //flag=true;
                }
                /* 
                if(flag=true)
                    break;
                    */
            }
        }
        return array;
    }

    public static void main(String[] args) {
        int[]a={1,3,45,34,2,42};
        int[] sort=sort(a);
        System.out.println(Arrays.toString(sort));
    }
}

稀疏数组

  • 是一种数据结构

  • 记录数组一共有几行几列,有多少不同值

  • 把具有不同值的元素和行列及值记录在一个小规模的数组中,缩小程序的规模

    public class ArrayDemo04 {
        public static void main(String[] args) {
            //创建一个二维数组
            int[][] array1 = new int[11][11];
            array1[1][2] = 1;
            array1[2][3] = 2;
            //输出原始数组
            System.out.println("输出原始的数组");
            for (int[] ints : array1) {
                for (int anInt : ints) {
                    System.out.print(anInt + "\t");
                }
                System.out.println();
            }
            //转换为稀疏数组
            int sum = 0;
            for (int i = 0; i < 11; i++) {
               for(int j=0;j<11;j++){
                   if(array1[i][j]!=0){
                       sum++;
                   }
               }
            }
            System.out.println("有效值的个数"+sum);
            //创建一个稀疏数组
            //行数即为非零个数加1,列数为3
            int[][]array2=new int[sum+1][3];
            array2[0][0]=11;
            array2[0][1]=11;
            array2[0][2]=sum;//非零值个数
            //遍历,找非零值
            int count=0;
            //行长度
            for(int i=0;i<array1.length;i++) {
                //列长度
                for (int j = 0; j < array1[i].length; j++) {
                    if (array1[i][j] != 0) {
                        count++;
                        array2[count][0] = i;
                        array2[count][1] = j;
                        array2[count][2] = array1[i][j];
                    }
                }
            }
                    //输出稀疏数组
                    System.out.println("稀疏数组");
                    for(int m=0;m<array2.length;m++){
                      System.out.println(array2[m][0]+"\t"+array2[m][1]+"\t"+array2[m][2]+"\t");
                    }
                    System.out.println();
    
            //还原
            //读取array2
            int[][]array3=new int[array2[0][0]][array2[0][1]];
            //给其他元素还原
            for(int n=1;n<array2.length;n++){
                array3[array2[n][0]][array2[n][1]]=array2[n][2];
            }
            //打印
            System.out.println("输出还原的数组");
            for(int[]ints:array3){
                for(int anInt:ints){
                    System.out.print(anInt+"\t");
                }
                System.out.println();
            }
            }
    }
    
    

在这里插入图片描述

对象

对象是什么

  • 面对对象编程(Object-Oriented Programming,OOP)

    本质:以类的方式组织代码,以对象的组织(封装)数据

  • 方法+属性——>类的成员;

    1. 属性(成员变量):对象(如Dog)所有的属性,具有性别\种类\尾巴·······(属性初始化不是必须的,有默认值)
    2. 方法:功能\动作,如睡\叫·······
  • 对象:就是变量,引用类型的变量

  • 对象:具体,静态的属性:属性

    ​ 动态的行为:方法

    类:抽象,对对象的抽象(把相同的、相似的“像”)

    类是对象的模板,就是一个模板

  • 特征:

    1. 封装
    2. 继承
    3. 多态

类和对象的创建和使用

  • 类是一种抽象的数据类型,它是对某一类事物整体描述\定义,但是并不能代表某一个具体的事物,类是抽象的
  • 对象是抽象概念的具体实例,对象是具体的(用动物,狗,蛇,动物是类,狗、蛇是对象)
  • 类的UML图
    在这里插入图片描述
对象是new出来的

使用new关键字创建对象

  1. 使用new关键字创建的时候,除了分配内存空间之外,还会给创建好的对象进行默认的初始化以及对类中的构造器的调用

  2. 类中的构造器:构造方法,是在进行创建对象的时候必须调用的

  3. 特点:a. 必须和类的名字相同

    ​ b. 必须没有返回类型,也不能写void

    public class Student{
    String name;//null
    int age;//0
    }
    //方法
    public void study(){
    System.out.println(this.name+"在学习");
    }
    public static void main(String[]args){
    //类:抽象的,要实例化
    //类实例化后会返回一个自己的对象
    //xh对象就是一个Student类的具体实例
    Student xh=new Student();//xh是引用类型的变量,可以表示一个对应的对象
    xh.name="小文";//对象的属性
    xh.age=3;
    xh.study();//对象的方法
    System.out.println(xh.name);
    System.out.println(xh.age);
    }
    }
    

    4.对象:属性:字段Filed 成员变量 修饰符 属性类型 属性名 =属性值;public char sex=M;

    默认初始化:数字:0 0.0

    char:u0000

    boolean:false

    引用数组:null

构造器

  • 作用:new实质在调用构造器(alt+insert 自动生成构造器)(注意有参/无参)

    初始化对象的值

  • 有默认构造器,调用无参构造,有有参构造时,无参构造得显示出来,没有有参构造时,不需要/可以显示无参构造

    //一旦定义了有参构造,无参就必须显示定义

    public class Person{
    String name;
    public person(){
    
    }//无参构造
    public person(String name){
    this.name=name;
    }//有参构造
    }
    public class Application {
        public static void main(String[] args) {
            //new实例化了一个对象
            Person person=new Person();
            System.out.println(person.name);//null
            Person person=new Person("xh");
            System.out.println("xh");//xh
        }
    }
    

封装

  • “高内聚,低耦合”:类内部数据操作细节自己完成,不允许外部干涉,仅仅暴露少量的方法给外部使用

  • 封装(数据的隐藏)

    信息隐藏:通常,应该禁止直接访问一个对象中数据的实际表示,而应该通过操作接口来反问

  • 属性私有(加private) get\set //方法不是私有的

    作用:

    1. 提高程序的安全性,保护数据
    2. 隐藏代码的实际细节
    3. 统一接口
    4. 系统可维护增加了
public class Application {
    public static void main(String[] args) {
       Student s1=new Student();
       s1.setName("xh");
       System.out.println(s1.getName());//xh
    }
}
public class Student {
    //属性私有
    private String name;//名字
    private int id;//学号
    private char sex;//性别

    //提供一些可以操作这个属性的方法
    //提供一些public的get,set方法
    //快捷键alt+insert可以自动生成get\set方法
    //get -获得这个数据
    public String getName() {
        return this.name;
    }
    //set 给这个数据设置值
    public void setName(String name){
        this.name=name;
    }
}

继承

继承
  • 继承:对某一批类的抽象,从而实现对现实世界更好的建模

  • extends:且类只有单继承(但是接口有多继承)

  • 继承是类和类之间的关系

    1. 类和类 ——>extends 1->1

    ​ 还有依赖、组合、聚合、继承等关系

    2.类和接口——>implements 1->n

    1. 接口和接口——>extends 1->n

    A extends B,C //A接口有B,C两个接口的方法

    D implements A //D能实现B,C两个接口的方法

  • 继承是子类(派生类)和父类(基类)的关系,子类extends父类

    public class Dog extends Animal{
    }
    
  • 继承的UML图
    在这里插入图片描述

  • 特点:

    1. 子类有父类的所有属性,子类继承了父类的所有成员变量和方法
    2. 一个父类可以由多个子类继承,一个子类只能继承一个父类,所有类默认继承object类
    3. 私有的东西无法被继承
    • 在父类的修饰词中,优先选用public,protected
修饰词本类同一个包中的类子类其他类
public可访问可访问可访问可访问
protected可访问可访问可访问不可访问
default(默认)可访问可访问不可访问不可访问
private可访问不可访问不可访问不可访问
super类
  • super用于访问父类中的成员变量

  • 注意点

    • super调用父类的构造方法,必须在构造方法的第一个
    • super必须只能出现在子类的方法或者构造方法中
    • super和this不能同时调用构造方法(它们要求都要在方法的第一个,只能二选一)
  • super VS this

    1. 代表对象不同
      • this:本身调用者这个形象
      • super:代表父类对象的应用
    2. 前提
      • this:没有继承也可以引用
      • super:只能在继承条件才可以使用
    3. 构造方法
      • this:本类的构造
      • super:父类的构造
  • 当调用构造器的时候,注意无参/有参,有参构造器一定要用到super()

  • 如果子类的构造方法中没有调用父类的构造方法,编译器会自动的加入对父类无参构造方法的调用 super()

    (如果该父类没有无参的构造方法,会编译错误)

public class Person{
super();//编译器自动加入
}
public class Person {
        protected String name="xh";
        public void print(){
                System.out.println("Person");
        }

}
public class Teacher extends Person {
    private String name="xh";
    public void print(){
        System.out.println("Teacher");
    }
    public void test1(){
        print();//Teacher
        this.print();//Teacher
        super.print();//Person
    }
}
public class Application {
    public static void main(String[] args) {
       Teacher t1=new Teacher();
       t1.test1();
    }
}
方法重写
  1. 与属性无关
  2. 需要有继承关系,子类重写父类的方法
  • 方法名必须相同
  • 参数列表必须相同
  • 修饰符:范围可以扩大但是不能缩小 public->protected->default->private
  • 抛出的异常:范围可以缩小,但不能扩大 ClassNotFoundException->Exception(大)
  1. 子类和父类的方法必要一致,方法体不同

  2. 注意静态的方法和非静态的方法区别很大:

    • 静态方法:方法的调用只和左边定义的数据类型有关(能执行哪些方法)
    • 非静态(重写)(private不能重写)
  3. 为什么要重写:子类不一定需要或者不一定满足父类的功能

    Alt+Insert 选override

    B b=new A();//子类重写了父类的方法
    b.test();//输出子类A中test()内容
    
  4. 重写使用super关键字

    子类在重写父类的方法时,可以通过super关键字调用父类的版本。
    在这里插入图片描述

7.重写和重载的区别

  • · 重载是指在一个类中定义多个方法名相同但参数列表不同的方法,在编译时,根据参数的个数和类型来决定绑定哪个方法。
  • · 重写是指在子类中定义和父类完全相同的方法,在程序运行时,根据对象的类型不同(而不是引用类型)而调用不同的版本。

多态

  • 多态是方法的多态,属性没有多态

  • 作用:使引用更灵活

  • 存在条件:继承关系,方法需要重写,父类引用指向子类对象

    Father f1=new Son();//f1.name是name Son()中的
    
    public class Student extends Person{
        public static void main(String[] args) {
            Student s1=new Student();
            Person s2=new Student();
            Object s3=new Student();
            s2.eat();//子类重写父类的方法
            s1.eat();
        }
        public void eat(){
            System.out.println("eat");
        }
    }
    public class Person {
        public void eat(){
            System.out.println("eat.eat");
        }
    }
    
    

类型转换

instanceof关键字
  • 要求:有继承关系

    ​ 类型之间的转换(同级转换,从属于继承关系,父与子)

    ​ 高——>低(比如Object->Person->Student)

public class Application {
    public static void main(String[] args) {
        //Object>String
        //Object>Person>Student
        //Object>Person>Teacher
        Object object=new Student();
        System.out.println(object instanceof Student);//true
        System.out.println(object instanceof Person);//true
        System.out.println(object instanceof Object);//true
        System.out.println(object instanceof Teacher);//false
        System.out.println(object instanceof String);//false
        Person obj=new Student();
         //将这个对象转换为Student类型,就可以使用Student
         ((Student).obj).go();
    }
}

自动类型转换
  • 低——>高

    Person person=student;
    
向上造型
  • 父类 a =new 子类对象
  • 父接口类型 =new 实现类对象
    public class Demo05 {
        public static void main(String[] args) {
            //创建子类对象,会先创建父类对象(调用父类的构造器)
            //向上造型---自动类型转换--低到高
            Animal a=new Dog();//a本质是引用
            //a.ask();会报错//不是重写
            // a是Animal类型,不能调用Dog类型的方法
            //a能调用的只有Animal中的方法,但最终使用的是Dog重写的方法
            //通过JVM可知a最后是Dog类型
            a=new Pig();//打印pig//如果没有该语句,则if语句为真,打印wan
            if(a instanceof Dog) {
                //强制类型转换(前提是虚拟机认为a是Dog类型
                Dog d1 = (Dog) a;
                d1.ask();
            }
        }
    }
    public class Animal {
        char sex;
        int age;
        //实体类规范:添加无参构造器,为了方便被继承
        public Animal(){
        }
        public Animal(int age){
            System.out.println("new Animal");
        }
        public void sleep(){
            System.out.println("sleep");
        }
        public void eat(){
            System.out.println("eat");
        }
    }
    public class Dog extends Animal{
        String name;
        //子类构造器中,第一行会默认添加 super()
        public Dog(){
            //创建子类构造器之前,一定先创建父类构造器
            super(10);//如果父类没有无参构造器,要么父类添加无参构造器,要么在子类中添加有参构造器
            System.out.println("new Dog");
        }
        public void ask(){
            System.out.println("wan");
        }
     public class Pig extends Animal {
        int weight;
        public Pig(){
            super();
            System.out.println("pig");
        }
    }
    

在这里插入图片描述

  1. 父类引用指向子类的对象
  2. 把子类转换为父类,向上转型(可能丢失一些自己本来的一些方法)
  3. 把父类转换为子类,向下转型,强制转换
  4. 方便方法的调用,减少重复的代码

static

  • static方法中不能对非static成员(对象成员)进行访问(静态)

  • static只执行一次

    public class Person {
        {
            System.out.println("富强");//匿名代码块
        }
        static{
            System.out.println("民主");//静态代码块
        }
        public  Person(){
            System.out.println("文明");//构造方法
        }
    
        public static void main(String[] args) {
            Person person=new Person();//打印出 民主 富强 文明 //加载顺序先静态>匿名>构造
            System.out.println();
            Person person1=new Person();//静态代码块只执行一次
        }
    }
    public class Student {
        private static int age;//静态的变量  多线程
        private double score;//非静态的变量
        public void run(){
            System.out.println("run");
        }
        public static void go(){
            System.out.println("go");
        }
        public static void main(String[] args) {
            Student s1=new Student();
            s1.run();
            go();//静态调用静态方法
        }//打印 run go
    }
    
  • 随机数+静态导入包

    import static java.lang.Math.random;
    public class Random {
        public static void main(String[] args) {
            System.out.println(Math.random());
        }
    }
    

抽象类

  1. abstract修饰符可以用来修饰方法也可以用来修饰类,

    如果修饰方法,那么该方法就是抽象方法;

    如果修饰类,那么该类就是抽象类。

  2. 抽象类可以没有抽象方法,但是抽象方法的类一定要声明为抽象类

  3. 抽象类,不能使用new关键字来创建对象,它是用来让子类继承的

  4. 抽象方法,只有方法的声明,没有方法的实现,它是让子类来实现的——>约束作用

  5. 不能同时使用final和abstract修饰类和方法——抽象类中的方法是要求被实现的,final是不能被更改的

  6. 抽象方法也不可以是static修饰的——被实现的方法能更改且重写—static只能使用一次

  7. 子类继承抽象类,那么就必须要实现抽象类没有实现的抽象方法,否则该子类也要声明为抽象类

    public abstract class Action{
    //abstract 抽象类
    }
    
  8. 作用:提高开发效率

接口

  • 普通类:只有具体实现

  • 抽象类:具体实现和规范(抽象方法)都有

  • 接口:只有规范!自己无法写方法 , 专业的约束!约束和实现分离:面向接口编程~

    • 接口本质就是契约,就是约束
    • 声明类的关键字是class,声明接口的关键字是interface
    • 接口都要有实现类
  • 接口的作用:

    • 可以用抽象方法表示重要的行为标准——约束
    • 可以把实现接口的类的对象的引用赋值给接口变量,该接口变量可以调用被该类实现的接口方法
      ​ ——体现了该类根据接口里的行为标准给出的具体行为
  • 接口的UML图
    在这里插入图片描述

创建接口

直接创建//将class改为interface

实现接口
  • 类可以实现接口 implements 接口
  • 实现了接口的类,就需要重写接口中的方法(放在爆红的位置,alt+enter键自动补充方法)
  • 实现接口的UML图
    在这里插入图片描述
public interface UserService {
    //接口中的所有定义都是抽象的
    int ASD=99;//常量都是public static final
    void add(String name);
    void delete(String name);
    void update(String name);
    void query(String name);//方法都是public static
}

public class UerServiceImp implements UserService{

    @Override
    public void add(String name) {

    }

    @Override
    public void delete(String name) {

    }

    @Override
    public void update(String name) {

    }

    @Override
    public void query(String name) {

    }
}
  • 特点

    1. 约束

    2. 定义一些方法,让不同的人实现—多态

    3. 多态:不同类实现同一接口可能有不同的实现方法,接口变量在回调接口方法时可能有多种形态

    4. 定义的方法都是public static

    5. 定义的常量都public static final

    6. 接口不能被实例化,接口中没有构造方法

    7. implements可以实现多个接口

    8. 接口也可以被继承——子接口与父接口关系

    9. 必须重写接口中的方法(非抽象类)

    10. 抽象类声明实现一个接口,但是可以不用重写接口中所有的方法
      ——抽象类可以重写接口中的方法,也可以直接拥有接口中的方法(即不用重写,被继承的类可以重写抽象类中的方法)

    public class UerServiceImp implements UserService,TimeService{
    //接口中的方法
    ···
    }
    
接口回调
  1. 声明接口变量
  2. 接口变量中存放对象的引用
  3. 接口回调
interface ShowMessage{
    void s(String s);
}

class mm implements ShowMessage{
      public void s(String s){
         System.out.println(s);
      };
}

public class Example{
     public static void main(String args[]){
       ShowMessage sm;//1.声明接口变量
       sm=new mm();//2.接口变量中存放对象的引用
       sm.s("你好呀!");//3.接口回调
}
}
接口和抽象类的比较
  • abstract类和接口都可以有抽象方法
  • 接口中只能有常量和抽象方法,不能有变量;抽象类中可以有常量、变量、抽象方法、非抽象方法

内部类

  1. 在一个类的内部再定义一个类A类中定义了一个B类 //A类是外部类,B类是内部类
  2. 分类
    • 成员内部类
    • 静态内部类 //加static
    • 局部内部类 //写在方法里
    • 匿名内部类
  3. 一个Java类中可有多个class类,但是只能有一个public class
public class Test {
    public static void main(String[] args) {
        //没有名字初始化类,不用将实例保存到变量中
        new Apple().eat();//匿名内部类
        UserService userService=new UserService() {
            @Override
            public void hello() {
            }
        };
public class Application {
    public static void main(String[] args) {
        Outer outer=new Outer();
        //通过外部类来实例化内部类
        Outer.Inner inner=outer.new Inner();
        inner.getID();
    }
}
        }
}
class Apple{
    public void eat(){
        System.out.println("1");
    }//成员内部类
}
interface UserService{
    void hello();                                                           
}
public class Application {
    public static void main(String[] args) {
        Outer outer=new Outer();
        //通过外部类来实例化内部类
        Outer.Inner inner=outer.new Inner();
        inner.getID();
    }
}
public class Outer {
    private int id=10;
    public void out(){
        System.out.println("这是外部类的方法");
    }
    public class Inner{
        public void in(){
            System.out.println("这是内部类的方法");
        }//成员内部类,可以打印id
        //获得外部类的私有属性
        public void getID(){
            System.out.println(id);
        }
        //静态内部类只要在内部类class前加一个static
        //但是这样无法打印出id,因为加载顺序是先   static,只能执行一次,这样就无法加载前面的
    }
}

异常

在这里插入图片描述

自定义异常
  • 使用Java内置的异常类可以描述在编程时出现的大部分异常情况。除此之外,用户自定义异常类,只需继承Exception类即可。
  • 在程序中使用自定义异常类,大体可分为以下几个步骤:
    1. 创建自定义异常类
    2. 在方法中通过throw关键字抛出异常对象
    3. 如果在当前抛出异常的方法中处理异常,可以使用try-catch语句捕获并处理; 否则在方法的声明处通过throws关键字指明要抛出给方法调用者的异常,继续进行下一步操作
    4. 在出现异常方法的调用者中捕获并处理异常
public class Exception {
    public static void main(String[] args) {
        int a=1;
        int b=0;
        
        try{//try监控区域
            System.out.println(a/b);
        }catch(ArithmeticException e){//catch捕捉异常
            System.out.println("程序出现异常,变量b不能为0");
        }finally{//处理善后工作
            System.out.println("finally");
        }
        //finally 可以不要finally,假设IO流,资源,关闭
    }
}

总结经验
  • 处理运行时异常时,采用逻辑去合理规避同时辅助try-catch处理
  • 在多重catch块后面,可以加一个catch (Exception) 来处理可能会被遗漏的异常
  • 对于不确定的代码,也可以加上try-catch ,处理潜在的异常
  • 尽量去处理异常,切忌只是简单地调用printStackTrace()去打印输出
  • 具体如何处理异常,要根据不同的业务需求和异常类型去决定
  • 尽量添加finally语句块去释放占用的资源

强烈推荐的视频讲解

点击跳转B站大神

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值