Java基础知识Part1

java特性

  • 面向对象(oop)
  • 健壮,Java的强类型机制、异常处理、垃圾的自动手机等是java程序健壮性的重要保证
  • 跨平台 [即:一个编译好的class文件可以在等多个系统下运行,这种特性称为跨平台]
  • 解释性

​ 解释性语言:JavaScript,PHP,Java 编译性语言:c/c++

​ 区别是:解释性语言,编译后的代码,不能直接被机器执行,需要解释器来执行,编译性语言,编译后的代码,可以直接被机器执行,c/c++

Java运行机制及运行过程

  • Java核心机制-Java虚拟机 [JVM java virtual machine]

基本介绍:

1)JVM是一个虚拟的计算机,具有指令集并使用不同的存储空间。负责执行指令,管理数据、内存、寄存器、包含在JDK中

2)对于不同平台,有不同的虚拟机

3)Java虚拟机制屏蔽了底层运行平台的差别,实现了“一次编译,到处执行”

Test.java -(编译 javac)——> Test.class -(运行 Java)——> JVM for LInux

​ ——> JVM for Windows

​ ——> JVM for Mac

什么是JDK JRE

  • JDK 基本介绍

    1. JDK的全称是(Java Development Kit Java开发工具包)

    ​ JDK = JRE + Java的开发功能工具[java javac javadoc javap等]

    2.JDK是提供给Java开发人员使用的,其中包含了Java的开发工具,也包含了JRE

    ​ 所以安装了JDK,就不用再单独安装JRE了

  • JRE基本介绍

    1.JRE(Java Runtime Environment Java 运行环境)

    ​ JRE = JVM + Java的核心类库[类]

    2.包括Java虚拟机(JVM Java Virtual Machine) 和Java程序所需的核心类库等,

    ​ 如果想要运行一个开发好的Java程序,计算机只需要安装JRE即可

Java开发细节

  • 编译后,每个类都对应一个.class
  • 如果原文件包含一个public类,则文件名必须按照该类名命名
  • 一个源文件最多只能有一个public类。其他类的个数不限,也可以将main方法写在非public类中,然后指定运行非public类,这样入口就是非public的主方法

Java基础

Java转义字符

  • \t: 一个制表位,实现对其的方法

  • \n: 换行符

  • \\ 一个\

  • \" 一个“sout

  • \’ 一个‘

  • \r 一个回车 System.out.printlin(“hello world”)

基本数据类型和String类型的转换

  • 介绍:

    在程序开发中,我们经常需要将基本数据类型转成String类型。或者将String类型转成基本数据类型

  • 基本类型转String类型:

    • 语法:将基本类型的值+ “” 即可

      public class Main {
      public static void main(String[] args) {
      int n1 = 100;
      float n2 = 1.1f;
      double n3 = 3.4;
      boolean b1 = true;
      String str1 = n1 + "";
      String str2 = n2 + "";
      String str3 = n3 + "";
      String str4 = b1 + "";
      System.out.println(str1 + " " + str2 + " " + str3 + " " + str4);
      }
      }

  • String类型转基本数据类型

    语法:通过基本类型的包装类调用parseXX的方法即可

    //String -> 对应的基本数据类型
    //使用 基本数据类型对应的包装类 的相应方法 得到基本数据类型
    String s5 = "123";
    int num1 = Integer.parseInt(s5);

    //怎么将字符串转成字符 -> 含义时将字符串的第一个字符得到 System.out.println(s5.charAt(0));

三元运算符

  • 基本语法:

条件表达式 ? 表达式1:表达式2;

  • 运算规则

    1.如果条件表达式为true,运算结果是表达式1;

    2.如果条件表达式为false,运算结果是表达式2;

    public class TernaryOperator {
        public static void main(String[] args) {
            //三元运算符使用
            int a = 10;
            int b = 99;
    
           int result = a > b ? a++ : b--;
           System.out.println(b);
      }
    }
    

键盘输入

  • 介绍:

    在编程中,需要接收用户输入的数据,就可以使用键盘输入语句来获取,需要一个扫描器,就是Scanner

  • 步骤:

    1)导入该类的所在包

    2)创建该类对象(声明变量)

    3)调用里面的功能

public class Input {
    public static void main(String[] args) {
        // 演示接收用户的输入
        //步骤
        //Scanner类 表示 简单文本扫描器 在java.util包
        //1.引入/导入 Scanner类所在的包
        //2.创建 Scanner 对象

        Scanner scanner = new Scanner(System.in);
        //3.接收用户的输入 使用 相关的方法
        System.out.println("请输入用户的名字");
        
        //当程序执行到 next方法时 会等待用户输入
        String name = scanner.next();   //接收用户输入字符串
        System.out.println("请输入用户的年龄");
        int age = scanner.nextInt();    //接收用户输入int
        System.out.println("请输入用户的薪水");
        double sal = scanner.nextDouble();  //接收用户输入double
        System.out.println("人的信息如下:");
        System.out.println("name=" + name + " age=" + age + " sal=" + sal);
    }
}

控制结构

多重循环控制

  • 经典的打印金字塔

    使用for循环完成以下案例

    请编写一个程序,可以接收一个整数,表示层数(totalLeval),打印出金字塔

    [先繁后简,先死后活]

public class Stars {
    public static void main(String[] args) {
        int totalLevel = 10; //层数
        
        for (int i = 1; i <= totalLevel; i++) {   //i 表示层数
            //在输出* 前还要添加空格
            for (int k = 1; k <= totalLevel - i; k ++) {
                System.out.print(" ");
            }
            for (int j = 1; j <= 2 * i - 1; j++) {  //j 表示打印每层*的个数
                //当前行的第一个位置时*,最后一个位置也是*,最后一层全部*
                if (j == 1 || j == 2 * i - 1 || i == totalLevel){
                    System.out.print("*");
                }else {
                    System.out.print(" ");
                }
            }
            System.out.println();
        }
    }
}
  • 化繁为简:即将复杂的需求,拆解为简单的需求,逐步完成
  • 先死后活:先考虑固定的值,然后转成可以灵活变化的值

数组

数组的使用

  • 使用方法1 - 动态初始化

    • 数组的定义

      • 数据类型[] 数组名 = new 数组类型[大小];
      • 数据类型 数组名[] = new 数组类型[大小];
      • int a[] = new int[5]
    • 数组的引用/使用/获取

      • 数组名[下标/索引/index]
        • a[2] 数组的下标从0开始
  • 使用方法2 - 动态初始化

    • 先声明数组

      • 没分配内存空间 null

      • 语法:数据类型 数组名[]; int a[];
      • 也可以:数据类型[] 数组名; int[] a;
    • 创建数组

      -> 分配内存空间,可以存放数据

      • 语法:数组名 = new 数据类型[大小] a = new int[6];
  • 使用方法3 - 静态初始化

    • 初始化数组

      • 语法:数据类型 数组名[] = {元素值,元素值…}

数组使用注意事项

  • 数组是多个相同类型数据的组合,实现对这些数据的统一管理
  • 数组中的元素可以是任意数据类型,包括基本数据类型和引用类型,但是不能混用
  • 数组创建后,如果没有赋值,有默认值
    • int 0
    • short 0
    • byte 0
    • long 0
    • float 0.0
    • double 0.0
    • char \u0000
    • boolean false
    • String null
  • 使用数组的步骤
    • 1.声明数组并开辟空间
    • 2.给数组各个元素赋值
    • 3.使用数组
  • 数组的下标是从0开始的
  • 数组下标必须在指定范围内使用,否则报:下标越界异常 ArrayIndexOutOfBoundsException
  • 数组属引用类型,数组型数据是对象(object)

数组赋值机制

1.基本数据类型赋值,这个值就是具体的数据,而且相互不影响

2.数组在默认情况下是引用传递,赋的值是地址

public class Eg5_ArrayAssign {
    public static void main(String[] args) {
        //基本数据类型赋值,赋值方式为值拷贝
        //n2的变化,不会影响n1的值
        int n1 = 10;
        int n2 = n1;

        n2 = 80;
        System.out.println("n1=" + n1);//10
        System.out.println("n2=" + n2);//80

        //数组在某人条件下是引用传递,赋的值是地址,赋值方式为引用传递/地址拷贝
        //是一个地址
        int[] arr1 = {1,2,3};
        // 数组的赋值,赋的值是地址
        int[] arr2 = arr1; //把arr1赋给 arr2
        arr2[0] = 10;

        //看看arr1的值
        System.out.println("=====arr1的元素=====");
        for (int i = 0; i < arr1.length; i++) {
            System.out.println(arr1[i]);
        }   //10 2 3

        //看看arr2的值
        System.out.println("=====arr2的元素=====");
        for (int i = 0; i < arr2.length; i++) {
            System.out.println(arr2[i]);
        }   //10 2 3
    }
}

数组拷贝

public class Eg6_ArrayCopy {
    public static void main(String[] args) {
        //将int[] arr1 = {10,20,30}; 拷贝到arr2数组,要求数据空间是独立的
        int[] arr1 = {10,20,30};

        //创建一个新的数组,开辟新的数据空间
        //大小 arr1.length
        int[] arr2 = new int[arr1.length];

        //遍历 arr1,把每个元素拷贝到对应的位置
        for (int i = 0; i < arr1.length; i++) {
            arr2[i] = arr1[i];
        }

        //修改 arr2
        arr2[0] = 100;

        //输出arr1
        System.out.println("=====arr1的元素=====");
        for (int i = 0; i < arr1.length; i++) {
            System.out.println(arr1[i]);
        }   //10 2 3

        //输出arr2
        System.out.println("=====arr2的元素=====");
        for (int i = 0; i < arr2.length; i++) {
            System.out.println(arr2[i]);
        }   //100 2 3
    }
}

数组反转

要求:把数组的元素内容反转

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

        //定义数组
        int[] arr = {11, 22, 33, 44, 55, 66};
    	//把arr[0] 和 arr[5] 进行交换
        //把arr[1] 和 arr[4] 进行交换 
        //把arr[2] 和 arr[3] 进行交换
        //共交换 3次 = arr.length / 2
        //每次交换时,对应的下标 是 arr[i] 和 arr[arr.length - 1 -i]
        int temp = 0;
        for (int i = 0; i < arr.length / 2; i++) {
            temp = arr[arr.length - 1 - i];;
            arr[arr.length - 1 - i] = arr[i]; //保存
            arr[i] = temp;
        }
    }
}

排序介绍

排序是将多个数据,依指定的顺序进行排列的过程

排序的分类

  • 内部排序法:

    指将需要处理的所有数据都加载到内部存储器中进行排序。包括(交换式排序法、排除式排序法和插入式排序法)

  • 外部排序法:

    数据量过大,无法全部加载到内存中,需要借助外部存储进行排序。包括(合并排序法和直接合并排序法)

冒泡排序法

基本思想:

通过对打排序序列从后向前(从下表较大的元素开始),一次比较相邻元素的值,若发现逆序则交换,使值较大的数逐渐从前移向后部,就像水底下的气泡一样逐渐向上冒

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SYJ7gkQJ-1682860783638)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230426181842058.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-8x8FOWLa-1682860783639)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230426182342925.png)]

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

        //化繁为简 先死后活

        int[] arr = {24, 69, 80, 57, 13, -1, 849};
        int temp = 0;   //用于辅助交换的变量
        //将多轮排序使用外层循环包括起来即可
        for (int i = 0; i < arr.length-1; i++) { //外层循环4次
            for (int j = 0; j < arr.length - 1 - i; j++) { //4次交换
                //如果前面的数 > 后面的数,就交换
                if (arr[j] > arr[j + 1]) {
                    temp = arr[j];
                    arr[j] = arr[j + 1];
                    arr[j + 1] = temp;
                }
            }
            System.out.println("===第" + (i + 1) +"轮===");
            for (int k : arr) {
                System.out.print(k + "\t");
            }
            System.out.println();
        }
    }
}

查找

  • 介绍

    在Java中,常用的查找有两种:

    • 顺序查找
    import java.util.Scanner;
    
    public class SeqSearch {
        public static void main(String[] args) {
            /*
            思路分析
            1.定义一个字符串数组
            2.接收用户输入,遍历数组,逐一比较,如果有,则提示信息,并退出
             */
    
            //定义一个字符串数组
            String[] names = {"白眉鹰王", "金毛狮王", "紫衫龙王", "青翼蝠王"};
            Scanner scanner = new Scanner(System.in);
            System.out.println("请输入名字");
            String findName = scanner.next();
    
            //遍历数组,逐一比较,如果有,则提示信息,并退出
    
            int index = -1;
            for (int i = 0; i < names.length; i++) {
                //比较 字符串比价 equals, 如果找到名字就是当前元素
                if (findName.equals(names[i])) {
                    System.out.println("恭喜你找到" + findName);
                    System.out.println("下标为" + i);
                    //把i 保存到index
                    index = i;
                    break;//退出
                }
            }
    
            if (index == -1) {  //没有找到
                System.out.println("sorry, 没有找到" + findName);
            }
        }
    }
    
    
    • 二分查找

二维数组介绍

  • 注意点

    • 二维数组的元素的个数:arr.length
    • 二维数组的每个一维数组的长度:arr[i].length
    • 二维数组的每一个元素都是一维数组, 所以如果需要得到每个一维数组的值还需要再次遍历
  • 使用方法1:动态初始化

    • 语法:类型[][] 数组名 = new 类型[大小][大小]

      • int a[][] = new int[2][3]
    • 二维数组在内存中的存在形式

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cIwjPywd-1682860783640)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230426201116673.png)]

  • 使用方式2:动态初始化

    • 先声明:类型 数组名[][];
  • 再定义(开辟空间) 数组名 = new 类型[大小][大小]

    • 赋值(有默认值,比如int类型的就是0)
  • 使用方法3: 列数不确定

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-zXLVQ3pC-1682860783640)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230426203133149.png)]

public class Test {
    public static void main(String[] args) {
        /*
        看一个需求:动态创建下面二维数组,并输出
        i = 0: 1
        i = 1: 2 2
        i = 2: 3 3 3

        一个有三个一维数组,每一个一维数组的元素是不一样的
         */

        int[][] arr = new int[3][]; //创建 二维数组,但是只是确定一维数组的个数,但是每个一维数组还没有开空间 new
        for (int i =0; i < arr.length; i++) { //遍历arr的每个一维数组
            //给每个一维数组开空间
            //如果没有给一维数组 new,那么 arr[i]就是null
            arr[i] = new int[i + 1];

            //遍历一维数组,并给一维数组的每个元素赋值
            for (int j = 0; j < arr[i].length; j++) {
                arr[i][j] = i + 1;//赋值
            }
        }
        //遍历arr输出
        for (int i = 0; i < arr.length; i++) {
            //输出arr的每个一维数组
            for (int j = 0; j < arr[i].length; j++) {
                System.out.print(arr[i][j] + " ");
            }
            System.out.println();
        }
    }
}
  • 使用方法4:静态初始化
    • 定义 类型 数组名[][] = {{值1,值2 …}, {值1, 值2…}, {值1, 值2…}}
    • 使用即可 [固定方式访问]

杨辉三角

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-MEcnOfK8-1682860783644)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230426205030168.png)]

public class YangHui {

    public static void main(String[] args) {

        int[][] yangHui = new int[10][];
        for (int i = 0; i < yangHui.length; i++) { //遍历yangHui的每个元素
            //给每个一维数组(行) 开空间
            yangHui[i] = new int[i+1];
            //给每个一维数组(行) 赋值
            for (int j = 0; j < yangHui[i].length; j++) {
                if (j == 0 || j == yangHui[i].length -1) {
                    yangHui[i][j] = 1;
                } else { //中间的元素
                    yangHui[i][j] = yangHui[i-1][j] + yangHui[i-1][j-1];
                }
            }
        }
        //输出杨辉三角
        for (int i = 0; i < yangHui.length; i++) {
            for (int j = 0; j < yangHui[i].length; j++) {
                System.out.print(yangHui[i][j] + "\t");
            }
            System.out.println();
        }
    }
}

二维数组使用细节和注意事项

  • 一维数组的声明方式有:

    int[] x 或者 int x[]

  • 二维数组的声明方式有

    int[][] y 或者 int[]y[] 或者 int y[][]

  • 三维数组实际上是由多个一维数组组成的,它的各个一维数组的长度可以相同,也可以不相同。比如:map[][] 是一个二维数组

    int map[][] = {{1,2}, {3,4,5}}

    由map[0]是一个含有两个元素的一维数组,map[] 是一个含有三个元素的一维数组构成,我们也称为列数不等的二维数组

类与对象

  • 类是抽象的,概念的,代表一类事物,比如人类、猫类、、

  • 对象是具体的,实际的,代表一个具体事物,即 是实例

  • 类是对象的模板,对象是类的一个个体,对应一个实例

  • 对象在内存中存在形式

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-zxWcPQq3-1682860783644)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230427120515141.png)]

属性和成员变量

基本介绍
  • 从概念或叫法上来看:成员变量 = 属性 = field字段 (即 成员变量是用来表示属性的)

  • 属性是类的一个组成部分,一般是基本数据类型,也可以是应用类型 (对象,数组)

注意事项和细节说明
  • 属性的定义语法同变量,示例:访问修饰符 属性类型 属性名 ;
  • 属性的定义类型可以为任意类型,包含基本类型或引用类型
  • 属性如果不赋值,有默认值,规则和数组一致

如何创建对象

  • 先声明再创建

    Cat cat; //声明对象 cat

    cat = new Cat(); //创建

  • 直接创建

​ Cat cat = new Cat();

如何访问属性

  • 对象名.属性名;
类与对象的内存分配机制

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9arAnK6g-1682860783645)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230427131450223.png)]

  • Java内存的结构分析

      1. 栈:一般存放基本数据类型(局部变量)
      2. 堆:存放对象 (Cat cat,数组等)
      3. 方法区:常量池(常量,比如字符串),类加载信息
      4. 示意图
  • Java创建对象的流程简单分析

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xGhAmB0m-1682860783645)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230427131929825.png)]

      1. 先加载Person类信息(属性或方法信息,只会加载一次)
      2. 在堆中分配空间,进行默认初始化(看规则)
      3. 把地址赋给 p,p就指向对象
      4. 进行指定初始化

成员方法

方法的调用机制原理

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jQenAayM-1682860783645)(C:\Users\输入你的姓名\AppData\Roaming\Typora\typora-user-images\image-20230427143145616.png)]

方法调用小结:

  1. 当程序执行到方法时,就会开辟一个独立的空间(栈空间)
  2. 当方法执行完毕,或者执行到return语句时,就会返回
  3. 返回到调用方法的地方
  4. 返回后,继续执行方法后面的代码
  5. 当main方法(栈)执行完毕,整个程序退出
为什么需要成员方法
  • 成员方法的好处

    • 提高代码的复用性
    • 可以将实现的细节封装起来,然后供其他用户来调用
  • 成员方法的定义

    访问修饰符 返回数据类型 方法名 (形参列表…) {

    ​ 语句

    ​ return 返回值;

    }

    1. 形参列表:表示成员方法输入 cal(int n), getSum(int num1, int num2)
    2. 返回数据类型: 表示成员方法输出,void 表示没有返回值
    3. 方法主体:表示为了实现某一功能代码块
    4. return语句不是必须的
注意事项
  • 方法修饰符

    如 果不写默认访问,(public, protected, private, 默认)

  • 返回数据类型

    1. 一个方法最多有一个返回值 [如何返回多个数据?返回数组]
    2. 返回类型可以为任意类型,包含基本类型(数组、对象)
    3. 如果方法要求有返回数据类型,则方法体中最后的执行语句必须为 return 值; 而且要求返回值类型必须和return的值类型一致或兼容
    4. 如果方法是void,则方法体中可以没有return语句,或者只写 return
  • 方法名

    遵循驼峰命名法,最好见名知意,表达出该功能的意思即可

  • 方法体

    里面写完成功能的具体的语句,可以为输入、输出、变量、运算、分支、循环、方法调用,但里面不能再定义方法,即:方法不能嵌套定义

  • 方法调用细节说明

    1. 同一个类中的方法调用:直接调用即可
    2. 跨类中方法A类调用方法B类:需要通过对象名调用。
    3. 跨类的方法调用和方法的访问修饰符相关
  • 成员方法传参机制

    • 基本数据类型的传参机制

      基本数据类型,传递的是值(值拷贝),形参的任何改变不影响实参!

    • 引用数据类型的传参机制

      引用类型传递的地址(传递的也是值,但是值是地址),可以通过形参影响实参

方法递归调用
  • 基本介绍:

    递归就是方法自己调用自己,每次调用时传入不同的变量。递归有助于编程者解决复杂问题,同时可以让代码变得简介

  • 递归重要规则

    1. 执行一个方法时,就创建一个新的受保护的对立空间(栈空间)

    2. 方法的局部变量是独立的,不会相互影响,比如n变量

    3. 如果方法中使用的是引用类型变量(比如数组,对象),就会共享该引用类型的数据

    4. 递归必须向退出递归的条件逼近,否则就是无限递归,出现StackOverflowError

    5. 当一个方法执行完毕,或者遇到return,就会返回,遵守谁调用,就将结果返回给谁,同时当方法执行完毕或者退出时,该方法也就执行完毕

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值