Java基础语法

基本的dos命令

打开cmd的方式

  1. 开始+系统+命令提示行
  2. Win+R 输入cmd打开控制台
  3. 在任意的文件夹下面,按住shift+鼠标右键,在此处打开命令行窗口
  4. 资源管理器的地址栏前面加上cmd路径

基本Dos命令

1. #盘符切换
2. #查看当前目录下所有文件 dir
3. #切换目录 cd \d(跨盘符操作) f:  cd.. 上返回级目录
4. #清理屏幕 cls (clear screen)
5. #退出终端 exit
6. #查看ip ipconfig
7. #打开应用
	calc 打开计算机
    mspaint 打开画图
    notepad 打开记事本
8. #创建目录 md 目录名
9. #删除目录 rd 目录名
11.#文件创建 copy con 文件名
10.#文件删除 del 文件名

java

IDE

集成开发环境。

第一个java程序

  1. 编写代码:
public class HelloWorld {
    public static void main(String[] args) {
        System.out.println("Hello,World!");
    }
}
  1. 在一个java文件所在位置。可在其前面加cmd

进入cmd命令,可以在文件所在位置执行

javac HelloWorld.java 编译HelloWorld.java文件

java HelloWorld.java 运行HelloWorld.java文件

image-20220417170703257

  1. java是大小写敏感的。
  2. 文件名 和 类名必须保持一致,并且首字母大写

java程序运行机制

  • 程序运行机制:

<1>java基础语法

1.注释、标识符、关键字

java中的注释有三种:

  • 单行注释 / /
  • 多行注释 /* */
  • 文档注释
    标识符注意点
  • 所有的标识符应该以字母(A-Z或a-z),美元符($),下划线(_)开始
  • 首字母之后可以是字母(A-Z或a-z),美元符($),下划线(_)和数字的任意组合
  • 标识符是大小写敏感的

2.数据类型★

强类型语言

​ 要求变量的使用符合规定,先定义后使用。

java数据类型分为两类,基本类型与引用类型

​ 基本数据类型:

​ byte占一字节范围:-128-127

​ short占两个字节范围:-32768-32767

​ int占四个字节范围:-2147483648-2147483647

​ long占八个字节 定义时在后面加L

​ float占四个字节

​ double占八个字节

​ 字符类型 char 占2个字节

​ Boolean类型:占一位只有true和false两个

​ 引用类型:

​ 类,接口,数组

//银行业务怎么表示?
//最好完全避免使用浮点数进行比较
//例如:
float f=0.1f;
double d = 1.0/1;

System.out.println(f==d); //false

float a1 = 2312312312312312313f;
float a2 = a1 + 1;

System.out.println(a1==a2); //true

3.类型转换

unicode编码,使得字符可以用数字表示。

char a='A'; (int)a=65.

4.变量、常量

//JDK7新特性,数字之间可以用下划线分割
int money = 10_0000_0000;
System.out.println(money);
//1000000000

public class Demo {
    
    //类变量 static
    static double salary = 2500;
    
    //实例变量:从属于对象;如果不自行初始化,默认值0
    //布尔值:默认值false
    //除了基本类型,其他默认值为null
    
    //类成员变量
    String name;
    int age;
    
    //main方法
    public static void main(String[] args){
        
        //局部变量:必须声明和初始化值
        int i = 10;
        System.out.println(i);
        
        //变量类型  变量名字 = new Demo();
        Demo demo1 = new Demo();
        System.out.println(demo1.age);
        System.out.println(demo1.name);
    }
    
    //其他方法
    public void add(){
        
    }
}

常量

初始化之后不能再改变值!不会变动的值。

final 常量名=值;
final double PI=3.14;

常量名一般用大写字符。

变量命名规范

所有变量、方法、类名:见名知意
类成员变量:首字母小写和驼峰原则:monthSalary
局部变量:首字母小写和驼峰原则
常量:大写字母和下划线:MAX_VALUE
类名:首字母大写和驼峰原则:Man,GoodMan
方法名:首字母小写和驼峰原则:run(),runRun()

5.运算符

同c语言
有位运算符。&,|,^,~,>>,<< 左移*2,右移/2.效率高
幂运算 用到 Math类。 Math.pow(2,3) Math.abs(-2)
很多运算会用到工具类去做。

//字符串连接符  +

int a=10;
int b=20;
System.out.println(""+a+b); 
//1020
System.out.println(a+b+"");
//30

//三元运算符
// x ? y : z
//如果x==true,结果位y,否则为z

6.包机制、JavaDoc

包机制

​ 为了更好的组织类,java提供了包机制,用于区别类名的空间。

​ 包的本质就是文件夹。

​ 包语法的语法格式为:

​ package pkg1[. pkg2[. pkg3...]];

​ 一般用公司域名倒置作为包名;

​ 为了能够使用某一个包的成员,我们需要在java程序中明确导入该包。使用"import" 语句可完成此功能。

​ import package1[.package2...].(classname | *); *是通配符,会导入包下面所有的类。

JavaDoc

javadoc命令是用来生产自己API文档的
参数信息

  • @author 作者名
  • @version 版本号
  • @since 指明需要最早使用的jdk版本
  • @param 参数名
  • @return 返回值情况
  • @throws 异常抛出情况

cmd 有 javadoc - encoding UTF-8 -charset UTF-8 Doc.java命令
格式为:javadoc 参数 Java文件 生成javadoc


<2>java流程控制

1.用户交互Scanner

java.util.Scanner 是Java5新特征,可以通过Scanner 类来获取用户的输入

基本语法:

Scanner s = new Scanner(System.in)

通过Scanner类的next()与nextLine()方法获取输入的字符串。在读取之前一般需要用 hasNext() 与 hasNextLine()判断是否还有输入的数据。

       //创造一个扫描器对象,用于接收键盘数据
        Scanner s = new Scanner(System.in);

        System.out.println("使用next方式接受:");

        //判断用户有没有输入字符串
        if(s.hasNext()){
            String str = s.next();
            System.out.println("输出的内容为:"+str);
        }

        //凡是属于IO流的类如果不关闭会一直占用资源,要养成好习惯用完就关掉
        s.close();

next():

​ 1.一定要读取到有效字符后才可以结束输入;

​ 2.对输入的有效字符之前的空白,next()方法会自动将其去掉;

​ 3.只有输入有效字符后才将其后面输入的空白作为分隔符或者结束符;

​ 4.next()方法不能得到带有空格的字符串

nextLine():

​ 1.以Enter为结束符,也就是说nextLine()方法是输出回车之前的所有字符;

​ 2.可以获得空白。

2.顺序结构

java基本结构就是顺序结构,除非特别指明,都是按照顺序一句一句执行

  public static void main(String[] args) {

        Scanner s = new Scanner(System.in);

        System.out.println("使用nextLine()方式接受:");

        String str = s.nextLine();

        System.out.println("输出的内容为:"+str);

        s.close();
    }

3.选择结构

包括 if单选择结构,if双选择结构,if多选择结构,嵌套的 if 结构,switch多选择结构。

   public static void main(String[] args) {

        Scanner scanner = new Scanner(System.in);
		
        System.out.println("请输入内容:");
        String s = scanner.nextLine();
		
       	//equals:判断字符串相等
        if(s.equals("Hello")){
            System.out.println(s);
        }
        scanner.close();
    }

4.循环结构

 public static void main(String[] args) {
		//输入多个数字,求其总和与平均数
        Scanner scanner = new Scanner(System.in);

        double sum=0;
        int num=0;

        //循环判断输入,并在里面进行求和统计,当输入非数字时结束输入,输出结果
        while(scanner.hasNextDouble()){
            double x = scanner.nextDouble();
            sum += x;
            num++;
        }

        System.out.println("总和为:"+sum+"\n平均数为:"+sum/num);

        scanner.close();
    }

while, for, do..while循环同c语言。不过java for循环在刚开始初始化进入循环时也会判断条件。

//增强for循环  同c++
for(声明语句 : 表达式){
	//代码句子
}
//声明语句:声明新的局部变量必须和数组元素的类型匹配。其作用域限定在循环语句块,其值与数组元素的值相等。
//表达式:表达式是要访问的数组名,或者是返回值为数组的方法。
//例如:
	int [] numbers = {10,20,30,40,50};
	for(int x:numbers){
		System.out.print(x+" ");
	}
//输出 10 20 30 40 50 

5.break&continue

break,continue同c。

关于goto关键字

  • goto关键字很早就在程序设计语言中出现,尽管goto仍是Java的一个保留字,但是并未在语言中得到正式使用:Java没有goto,然而,在break和continue这两个关键字的身上,我们仍然能看出一些goto的影子---带标签的break和continue

  • “标签”是指后面跟一个冒号的标识符,如:label:

  • 对Java来说唯一用到标签的地方是在循环语句之前,而在循环之前设置标签的唯一理由是:我们希望在其中嵌套的另一个循环,由于break和continue通常只中断当前循环,但若随同标签使用,他们就会中断到存在标签的地方。

    	//输出101-150之间的所有的质数
    
    	outer:for(int i=101;i<150;i++){
    		for(int j=2;j<i/2;j++){
    			if(i%j==0){
    				continue outer;
    			}
    		}
    		System.out.println(i);
    	}
    

6.练习

//打印5行三角形
       for (int i = 1; i <= 5; i++) {

            for(int j=5;j>i;j--)
                System.out.print(" ");

            for(int j=1;j<=i;j++)
                System.out.print("*");
            for(int j=1;j<i;j++)
                System.out.print("*");

            System.out.println();

<3>Java方法

1.方法的定义和调用

System.out.println(),那么他是什么呢?

​ System是一个系统的类,out是一个对象,println()是一个方法.

即:调用系统System类里out对象里的println方法。

Java方法是语句的集合,他们在一起执行一个功能

  • 方法是解决一类问题的步骤的有序组合
  • 方法包含于类或对象中
  • 方法在程序中被创建,在其他地方被引用

设计方法的原则:

​ 方法的本意是功能块,就是实现某个功能的语句块的集合。我们设计方法的时候,最好保持方法的原子性,就是一个方法只能完成一个功能,这样利于我们后期的扩展。

方法的定义

​ java的方法类似与其他语言的函数,是一段用来完成特定功能的代码片段,一般情况下,定义一个方法包含一下语法:

/*
·修饰符:可选的,告诉编译器如何调用该方法,定义了该方法的访问类型
·返回值类型:方法可能会返回值。returnValueType 是返回值的数据类型。有些方法执行所需的操作,但没有返回值。这种情况下,returnValueType 是关键字void。
·方法名:是方法的实际名称。方法名和参数表共同构成方法签名。
·参数类型:参数像是一个占位符。当方法被调用时,传递值给参数。这个值被称为实参或者变量。参数是可选的,方法也可以不包括任何参数。
	形式参数:在方法被调用时用于接收外界输入的数据。
	实参:调用方法时实际传递给方法的数据。
·方法体:方法体包含具体的语句,定义该方法的功能。
*/

修饰符  返回值类型  方法名(参数类型 类型名){
    ···
    方法体
    ···
    return 返回值。
}

方法调用

调用方法:对象名.方法名(实参列表)

java支持两种调用方法方式,根据是否返回值来选择。

int larger = max(30,40);

run();

return 0;//终止方法

搜索了解:值传递(Java) 和 引用传递。

2.方法的重载

重载就是在一个类中,有相同的函数名称,但形参不同的函数。

方法重载的规则:

  • 方法名称必须相同
  • 参数列表必须不同(个数不同,或类型不同,参数排列顺序不同等)
  • 方法的返回类型可以相同可以不同
  • 仅仅返回类型不同不足以称为方法的重载

实现理论:

​ 方法名称相同时,编译器会根据调用方法的参数个数、参数类型逐个去匹配,以选择对应的方法。如果匹配失败,则报错。

3.命令行传递参数

​ 有时候你希望运行一个程序的时候再传递给他消息。这要靠传递命令行参数给main()函数实现。

public class CommandLine {
    public static void main(String[] args) {
        for(int i=0; i<args.length;i++){
       	   System.out.println("args["+i+"]"+args[i]);
       }
    }
}

cmd中执行:

文件路径下: javac Demo3_command.java 编译

直接 java Demo3-command 会报错:无法加载主类Demo3_command

需要路径移到src目录下 java com.lv.Method.Demo3_command

java com.lv.Method.Demo3_command this is black

//输出:

args[0]: this

args[1]: is

args[2]: black

4.可变参数

在方法声明中,在指定参数类型后加一个省略号(...)

一个方法只能电指定一个可变参数,它必须是方法的最后一个参数,任何普通的参数必须得在它之前声明。

public static int printMax(double ... numbers)

了解即可。

5.递归

递归就是:A方法调用A方法!自己调用自己。

递归写的简洁,但是如果传入参数过大的话,性能慢。

<4>数组

1.数组声明创建

数组的定义:

​ 数组是相同类型数据的有序集合。

​ 其中,每一个数据称作一个数组元素,每个数组元素可以通过一个下标来访问他们。

数组声明创建:

​ 首先必须声明数组变量,才能在程序中使用数组。

dataType[] arrays;  //首选方法
dataType  arrays[]; //效果相同,但不是首选方法

​ java方法用new操作符来创建数组,语法如下

dataType[] arrays = new dataType[arraysize]

​ 数组的元素是通过索引访问的,从0开始

​ 获取数组长度:arrays.length.

内存分析:

​ Java内存分析:

​ 堆:存放new的对象和数组,可以被所有的线程共享,不会存放别的对象引用;

​ 栈:存放基本变量类型(包含这个基本变量的具体数值),引用对象的变量(会存放这个引用在堆立面的具体地址)

​ 方法区:可以被所有的线程共享,包含了所有的class和static变量

三种初始化:

//静态初始化
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;

2.数组特点

数组的四个基本特点:

  • 其长度是确定的,一旦被创建,大小不可变
  • 其元素必须是相同类型,不允许出现组合类型
  • 数组中的元素可以是任何数据类型,包括基本类型和引用类型。
  • 数组变量属引用类型,数组也可以看成是对象,数组中的每个元素相当于该对象的成员变量。数组本身就是对象,Java中对象是在堆中的,因此数组无论保存原始类型还是其他对象类型,数组对象本身是在堆中的。

3.多维数组

//二维数组
int a[][] = new int[2][5];
//可以看出一个两行五列的数组

多维数组是数组的数组。具体同c。

4.Arrays类

数组的工具类 Java.util.Arrays

Arrays类中的方法都是static修饰的静态方法,在使用的时候可以直接使用类名进行调用,而“不用”使用对象来调用(注意:是不用,不是不能)

具有以下常用功能:

​ 给数组赋值:通过fill方法。

​ 给数组排序:通过sort方法。

​ 比较数组: 通过equals 方法比较数组中元素是否相等。

​ 查找数组元素:通过binarySearch 方法能对排序好的数组进行二分查找法操作。

5.扩展:稀疏数组

​ 当一个数组中大部分元素位0,或者为同一值的数组时,可以使用稀疏数组来保存该数组。

稀疏数组处理方式:

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

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

压缩算法。

package com.lv.array;

public class Demo5_xishu {
    public static void main(String[] args) {

        //1.创建一个二维数组11*11  0:没有棋子 1:黑棋 2:白棋
        int array1[][] = new int[11][11];
        array1[1][2] = 1;
        array1[2][3] = 1;
        //2.输出原始数组
        System.out.println("输出原始的数组:");

        for(int[] ints : array1){
            for(int anInt : ints) {
                System.out.print(anInt+"\t");
            }
            System.out.println();
        }

        //转换为稀疏数组保存
        //1.获取有效值的个数
        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);

        //2.创建一个稀疏数组
        int array2[][] = new int[sum+1][3];

        array2[0][0]=11;
        array2[0][1]=11;
        array2[0][2]=sum;

        //3。遍历二维数组,将非零的值,存放在稀疏数组中
        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];
                }
        //4.输出稀疏数组
        System.out.println("稀疏数组:");
        for (int i = 0; i < array2.length; i++) {
            System.out.println(array2[i][0]+"\t"+array2[i][1]+"\t"+ array2[i][2]);
        }


        //还原稀疏数组
        System.out.println("还原:");

        //1.读取稀疏数组
        int array3[][] = new int[array2[0][0]][array2[0][1]];

        //2.给其中的元素还原它的值
        for (int i = 1; i < array2.length; i++) {
            array3[array2[i][0]][array2[i][1]] = array2[i][2];
        }

        //3.打印
        System.out.println("还原的数组为:");
        for(int ints[] : array3){
            for(int anInt : ints)
                System.out.print(anInt + "\t");
            System.out.println();
        }

    }
}

<5>面向对象

1.什么是面向对象

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

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

三大特性: 封装、继承、多态。

从代码运行角度看:是先有类后有对象,对象是类的模板

面向对象 & 面向过程

面向过程思想:

​ 步骤清晰简单,第一步做什么,第二步做什么
​ 面向过程适合处理一些简单的问题

面向对象思想:

​ 物以类聚,分类的思维模式,思考问题首先解决问题需要哪些分类,然后对这些分类进行单独思考。最后,才对某个分类下的细节进行面向过程的思考。
​ 面向对象适合处理复杂的问题,适合处理需要多人协作的问题!

2.回顾方法及加深

方法的调用

静态方法:

//同一个包内的一个文件
//学生类
public class Student{
	//静态方法
	public static void say(){
		System.out.println("学生说话");
	}
}
//另一个文件
public class Demo1{
    
    public static void main(){
    	//静态方法可以,类名.方法直接调用
        Student.say();
    }
}

动态方法:

//同一个包内的一个文件
//学生类
public class Student{
	//非静态方法
	public static void say(){
		System.out.println("学生说话");
	}
}
//另一个文件
public class Demo1{
    
    public static void main(String[] args){
    	//实例化这个类 new
        //对象类型  对象名 = 对象值;
        Student student = new Student();
        
        student.say();
    }
}

​ 同时如果是动态方法,需要实例化后才可以加载。

public class Demo1 {
	
	public static void main(String[] args){...}
	
	//和类一起加载
	public static void a(){
		b();//报红,因为类没有实例化,b方法不存在
	}
	
	//类实例化后才存在
	public void b(){
	
	}
}

​ 形参实参

​ 同c

​ 值传递和引用传递

//引用传递,实质还是值传递
public class Demo1 {
	public static void main(String[] args){
		//实例化	
		Person person = new Person();
		
		System.out.println(person.name); //null
		
		change(person);
		
		System.out.println(person.name);//小明
	}
	
	public static void change(Person person){
		person.name = "小明";
	}
}

//定义了一个Person类,有一个属性:name
//类似于c里的结构体
class Person{
    String name; //null
}

​ this 关键字

3.类与对象的创建

(1)类与对象的关系

类是一种抽象的数据类型,它是对某一类事物的整体描述/定义,但是并不能代表某一个具体事物。

​ 动物、植物、手机、电脑

​ Person类、Pet类、Car类等,这些类都是用来描述/定义一类具体的事物应该具备的特点与行为。

对象是抽象具体概念的具体实例

​ 张三就是人的一个具体实例,张三家里的旺财就是狗的一个具体实例

​ 能够体现处特点,展现出功能的是具体的实例,而不是一个抽象概念

(2)创建与初始化对象

使用new关键字创建对象

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

类中的构造器也称为构造方法,是在进行创建对象的时候必须要调用的。并且构造器有一下两个特点:

​ 1. 必须和类的名字相同;

	2. 必须没有返回类型,也不能写void。
//同一个包里的其中一个文件
public class Student {
	//属性:字段
	String name; //null
	int age; //0
	
	//方法
	public void study(){
		System.out.println(this.name+"在学习");
	}
}
//另一个文件
public static void main(String[] args){
	
	//类,抽象化,实例化
	//类实例化后会返回以一个自己的对象!
	//student对象就是一个Student类的具体实例!
	
	Student xiaoming = new Student();
	Student lucy = new Student();
	
	xiaoming.name = "小明";
	xiaoming.age = 18;
	
	System.out.println(xiaoming.name);
	System.out.println(xiaoming.age);
	//小明
	//18
}

4.构造器详解

//同一个包里的其中一个文件
public class Person {

	//一个类即使声明都不做,也会存在一个方法
	//显示的定义构造器

	String name; 

	//实例化初始值
    //1. 使用new关键字,本质是在调用构造器
    //2. 用来初始化值
    public Person(){
      
    }
  
    //有参构造:一旦定义了有参构造,无参就必须显示定义
	public Person(String name){
		this.name = name;
	}
  
}
//另一个文件
  public static void main(String[] args) {

        //new 实例化了一个对象
        Person person1 = new Person();
        Person person2 = new Person("jack");
        Person person3 = new Person("lucy",18);

        System.out.println(person1.name+' '+person1.age); // null 0
        System.out.println(person2.name+' '+person2.age); // jack 
        System.out.println(person3.name+' '+person3.age); // lucy 18
    }

alt + insert 快捷键,构造构造器。

5.创建对象内存分析

![内存对象分析](C:\Users\lenovo\Documents\Tencent Files\2498626192\Image\QQ图片20220425194000.jpg)

6.封装详解

该露的露,该藏得藏

​ 我们程序设计要追求"高内聚,低耦合"。高内聚就是类的内部操作细节自己来完成,不允许外部干涉;低耦合:仅暴露少量的方法供给外部使用。

封装(数据的隐藏)

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

: 属性私有 get/set

  //同一个包里其中一个文件
   public static void main(String[] args) {
        Student s1 = new Student();

        s1.setName("Jack");

        System.out.println(s1.getName());
    }
    
//另一个文件
//类  private:私有
public class Student {

    //属性私有
    private String name; // 姓名
    private int id; // 学号
    private char sex; // 性别

    //提供一些可以操作这个属性的方法!
    // 提供一些public的 get、set方法

    //get方法 获得这个数据
    public String getName() {
        return this.name;
    }
	//set方法 给这个数据设置值
    public void setName(String name) {
        this.name = name;
    }

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public char getSex() {
        return sex;
    }

    public void setSex(char sex) {
        this.sex = sex;
    }

alt+insert 快捷键可以快速生成get/set方法。

封装作用:

  1. 提高程序的安全性,保护数据
  2. 隐藏代码的实现细节
  3. 统一接口
  4. 系统可维护性增加

7. 继承详解

(1) 什么是继承

继承的本质是对某一批类的抽象,从而实现对现实世界的更好的建模。

extends的意思是”扩展“。子类是父类的拓展。

Java中只有单继承,没有多继承。

继承关系的两个类,一个为子类(派生类),一个为父类(基类),子类继承父类,使用关键字extends来表示。

在Java中,所有的类都直接或间接继承object类。

//同一个包里的父类文件Person
//在Java中,所有的类都默认或直接间接继承object类。
//Person 人 :  父类
public class Person {

    //public
    //protected
    //default
    //private
    String name;

    public void say(){
        System.out.println(this.name+" say a word");
    }

//子类文件Student
//学生 is 人: 派生类,子类
//子类继承了父类,就会拥有父类的全部方法!
public class Student extends Person {

}
(2) super详解

私有的东西无法被继承

父类文件:

//在Java中,所有的类都默认或直接间接继承object类。
//Person 人 :  父类
public class Person {

    //public
    //protected
    //default
    //private
    protected String name = "protectedjack";

    public Person(){
        System.out.println("Person被执行了");
    }
    public void print(){
        System.out.println("Person");
    }

}
子类文件:

//学生 is 人: 派生类,子类
//子类继承了父类,就会拥有父类的全部方法!
public class Student extends Person {

    public Student(){
        //隐藏代码,调用了父类的无参构造
        super(); //调用父类的构造器,必须要在子类构造器的第一行
        System.out.println("Student无参执行了");
    }

    private String name = "jack";

    public void print(){
        System.out.println("Student");
    }

    public void  test1(){
        print(); //Student
        this.print(); //Studnet
        super.print();  //Person   super调用父类方法
    }
}

应用:
package com.lv.oop.demo05;

public class Application {
    public static void main(String[] args) {

        Student student = new Student();

        student.test1();
    }
}
/*
Person被执行了      
Student无参执行了
Student
Student
Person
*/

super注意点:

1. super调用父类的构造方法,必须在构造方法中的第一个

2. super 必须只能出现在子类的方法或者构造方法中

3. super 和 this 不能同时调用构造方法!

super 与 this 区别:

1. 代表对象不同:

	this:本身调用这个对象

	super:代表父类对象的应用

2. 前提

	this:没有继承也可以使用

	super:只能在继承条件下才可以使用

3. 构造方法

	this():本类的构造

	super():父类的构造
(3) 方法重写

子类重写父类的方法。(子类和父类有方法名称一样,但是功能不同,即需要重写)

子类:
public class A extends B{
    public static void test(){
        System.out.println("A=>test()");
    }
}
父类:
//重写都是方法的重写,与属性无关
public class B {
    public static void test(){
        System.out.println("B=>test()");
    }
}
应用:
public class Application {
    public static void main(String[] args) {

        //Student student = new Student();

        //student.test1();

        //方法的调用之和左边,定义的类型有关
        A a = new A();
        a.test();  //A=>test()

        //父类的引用指向了子类
        B b = new A();
        b.test();  //B=>test()
    }
}

如果我们把子类父类方法里的static去掉,会看见一个 O↑ 和O↓ 这个就是重写的标志

输出为:

A=>test()
A=>test()

因为静态方法是类的方法,非静态方法是对象的方法。有static时,b调用了B类的方法,因为b是用B类定义的。 没有static时,b调用的是对象的方法,而b是用A类new的,即b是A new出来的对象,因此调用了A的方法。

重写:需要有继承关系,子类重写父类的方法!

1. 方法名必须相同

2. 参数列表必须相同

3. 修饰符:范围可以扩大但不能缩小:  public > Protected > Default > private

4. 抛出的异常:范围可以被缩小但不能扩大:ClassNotFoundException --> Exception(大)

<6>异常机制

1.什么是异常、

  • 实际工作中,遇到的情况不可能是完美的。比如:你写的某个模块,用户输入不一定符合你的要求,你的程序要打开某个文件,这个文件可能不存在或者文件格式不对,你要读取数据库的数据,数据可能是空的等等……
  • 软件程序在运行过程中,非常可能遇到刚刚提到的这些异常问题,我们叫做异常(Exception),意思是例外情况
  • 异常指程序运行中出现的不期而至的各种状况,如:文件找不到、网络连接失败、非法参数等
  • 异常发生在程序运行期间,它影响了正常的程序执行流程

简单分类,分为以下三种的异常:

  • 检查性异常:最具代表性的检查性异常就是用户错误或问题引起的异常,这是无法预见的。例如要打开一个不存在的文件时,一个异常就发生了,这些异常在编译时不能被简单地忽略
  • 运行时异常:运行时异常是可能被程序员避免的异常,与检查性异常相反,运行时异常可以在编译时被忽略
  • 错误ERROR:错误不是异常,而是脱离控制的问题。错误在代码中通常被忽略。例如 当栈溢出时,一个错误就发生了,它们在编译也检查不到的。

2.异常体系结构

​ Java可以把异常当作对象来处理,并定义了一个 基类 java.lang.Throwable作为锁头的异常的超类

​ 在Java API中已经定义了许多异常类,这些异常类分为两大类,错误ERROR和异常Exception。

(1) Error错误

​ Error类对象由 Java虚拟机生成并输出,大多数错误与代码编写者所执行的操作无关

​ Java虚拟机运行错误 (Virtural MachineError),当JVM不再有继续执行操作所需要的内存资源时,将出现 OutOfMemoryError。当这些异常发生时,Java虚拟机(JVM) 一般会选择线程终止;

​ 还有发生在虚拟机试图执行应用时,如 类定义错误 (NoClassDefFoundError) 、链接错误 (LinkageError)。这些错误是不可查的,因为他们在应用程序中的控制和处理能力之外,而且绝大多数是程序运行时不允许出现的状况。

(2) Exception异常

在Exception分支中有一个重要的子类RuntimeException (运行时异常)

  • ArrayIndexOutOfBoundsException (数组下标越界)
  • NullPointerException (空指针异常)
  • ArithmeticException (算术异常)
  • Missing ResourceException (丢失资源)
  • ClassNotFoundException (找不到类) 等异常,这些异常是不检查异常,程序中可以选择捕获处理,也可以不处理

这些异常一般是由程序逻辑错误引起的,程序应该从逻辑角度尽可能避免这类异常发生;

Error 和 Exception的区别:

  • ​ Error 通常会是灾难性的致命性错误,是程序无法控制和处理的,当出现这些异常时,Java虚拟机(JVM)一般会选择中止线程;
  • ​ Exception 通常情况下是可以被程序处理的,并且在程序中应该尽可能去处理这些异常

3.Java异常处理机制

五个关键字:try、catch、finally、throw、throws

throw 抛出异常

public class Test2 {
    public static void main(String[] args) {

        try {
            new Test2().test(1,0);
        }catch (ArithmeticException e){
            e.printStackTrace();
        }

    }
    //假设方法中,处理不了这个异常,方法上抛出异常
    public void test(int a,int b) throws ArithmeticException{

        if (b==0){
            throw new ArithmeticException(); //主动抛出异常,一般在方法中使用
        }
    }

4.处理异常

catch()

public class Test {
	public static void main(String[] args) {
		int a=1;
        int b=0;
        //假设要捕获多个异常,要从小到大! 快捷键:Ctrl + Alt + T
        try { //监控区域
            new Test().a();
            System.out.println(a/b);
        }catch (Error e) {
            System.out.println("Error!");
        }catch (Exception e) {
            System.out.println("Exception!");
        }catch (Throwable e){ //catch(想要捕获的异常类型!)
            System.out.println("程序出现异常"); //如果出现对应的异常,会执行catch里操作
        }finally { //处理善后工作  最后肯定执行
            System.out.println("finally");
        }
    }
    public void a(){b();}
    public void b(){a();}
}

5.自定义异常

使用Java内置的异常类可以描述在编程时出现的大部分异常情况。除此之外,用户还可以自定义异常,只需继承Exception类即可。

在程序中使用自定义异常类,大体可以分以下几个步骤:

  1. 创建自定义异常类
  2. 在方法中通过throw关键字抛出异常对象
  3. 如果在当前抛出异常的方法中处理异常,可以使用try-catch语句捕获并处理;否则在方法的声明处通过throws关键字指明要抛出给方法调用者的异常,继续进行下一步操作
  4. 在出现异常方法的调用者中捕获并处理异常
//自定义异常类MyException
public class MyException extends Exception{

    //如果传递数字>10;抛出异常
    private int detail;

    public MyException(int a){
        this.detail = a;
    }

    @Override
    public String toString() {
        return "MyException{" + "detail=" + detail + '}';
    }
}
//Test 测试
public class Test {
    public void test(int a) throws MyException {

        System.out.println("传递的参数为"+a);
        if(a>10)
            throw new MyException(a);
        System.out.println("OK 不大于10");
    }

    public static void main(String[] args) {
        try {
            new Test().test(11);
        } catch (MyException e) {
            System.out.println("MyException =>" + e);
        }
    }
}
/* 输出结果:
传递的参数为11
MyException =>MyException{detail=11}
*/
posted @ 2023-01-05 12:16  1vxyz  阅读(41)  评论(0编辑  收藏  举报