第一课-----java介绍
目录
一、什么是Java
Java是一种基于类的面向对象的编程语言。语言是人与人交流沟通的表达方式,而人与计算机之间进行信息交流沟通的一种特殊语言就是计算机语言,也叫编程语言,java就是其中非常火的一门编程语言。我们想要让计算机做一些事情,那么就可以通过Java语言告诉计算机就可以了。它是用于应用程序开发的计算平台。因此,Java是快速,安全和可靠的。它被广泛用于在笔记本电脑,数据中心,游戏机,科学超级计算机,手机等中开发Java应用程序。Java遵循WORA(Write Once, Run Anywhere。一次写入,到处运行)的原理,并且与平台无关。
Java的主要特性
- 面向对象
- 安全性
- 多线程
- 简单易用
- 开源
- 跨平台
二、JDK、JRE、JVM
JVM(Java Virtual Machine),Java虚拟机。JVM 是可运行 Java 代码的假想计算机 ,包括一套字节码指令集、一组寄存器、一个栈、 一个垃圾回收,堆和 一个存储方法域。JVM 是运行在操作系统之上的,它与硬件没有直接的交互。我们都知道 Java 源文件,通过编译器,能够生产相应的 .Class 文件,也就是字节码文件, 而字节码文件又通过 Java 虚拟机中的解释器,编译成特定机器上的机器码 。 也就是如下:
Java 源文件 --> 编译器 --> 字节码文件 --> JVM --> 机器码
每一种平台的解释器是不同的,但是实现的虚拟机是相同的,这也就是 Java 为什么能够跨平台的原因了 ,当一个程序从开始运行,这时虚拟机就开始实例化了,多个程序启动就会存在多个虚拟机实例。程序退出或者关闭,则虚拟机实例消亡,多个虚拟机实例之间数据不能共享。
JRE(Java Runtime Environment),Java运行环境,包含了JVM和Java的核心类库(Java API)。Java 运行时环境(简称 JRE)是一个软件层,它在计算机的操作系统软件之上运行,提供特定 Java 程序运行所需的类库和其他资源。JRE 将使用 JDK 创建的 Java 代码与在 JVM 上运行代码所需的必要库相结合,然后创建一个 JVM 实例以执行生成的程序。 JVM 可用于多个操作系统,使用 JRE 创建的程序可在所有操作系统上运行。 通过这种方式,Java 运行时环境使 Java 程序无需修改即可在任何操作系统中运行。
JDK(Java Development Kit)称为Java开发工具,包含了JRE和开发工具。JDK 是一个软件包,其中包含各种工具和实用程序,可以开发、打包、监控和部署为任何标准 Java 平台构建的应用程序,包括 Java 平台标准版 (Java SE); Java 平台,微型版 (Java ME);和 Java 平台企业版 (Java EE)。
JDK和JVM的区别
在 JDK bin 目录中,还有一个名为 java 的实用程序。该实用程序将采用任何包含可运行 main 方法的 Java 应用程序并将其作为软件程序执行。当 Java 应用程序的源代码被编译时,它被编译成字节码。字节码是 Java 源代码和低级机器代码之间的中介。当调用 java 实用程序时,会创建一个 JVM,它使用即时 (JIT) 编译器将字节码转换为机器码。这种从 Java 字节码到低级计算机指令的即时转换是使 Java 应用程序跨平台和硬件无关的关键。
Java语言跨平台的原理
操作系统本身其实是不认识Java语言的。但是针对于不同的操作系统,Java提供了不同的虚拟机。虚拟机会把Java语言翻译成操作系统能看得懂的语言。
JDK 与 JRE 比较
下载和安装 Java 时,有两种可能的选择。第一种是下载安装JRE,第二种是下载安装JDK。任何用 Java 编写的程序,除了标准的 Java 库集和简单的执行环境之外,不需要任何额外功能,都可以在 JRE 提供的 JVM 上成功运行。但是,如果需要任何补充功能,例如需要即时编译 Java 源代码或生成身份验证证书,则需要 JDK。JDK 包含自己的 JRE,但在 JRE 的基本功能之外还提供了各种额外的功能。
三、Java平台
Java是SUN公司(斯坦福大学网络公司)1995年推出的一门高级编程语言。是一种面向Internet的编程语言,随着Java技术在Web方面的不断成熟,已经成为Web应用程序的首选开发语言。
Java包括Java语言和Java平台
JavaSE(Java Platform Standard Edition,标准版),用来开发桌面应用、C/S结构网络应该是JavaEE的基础,是Java技术体系的核心,是其他两个版本的基础。
JavaEE(Java Platform,Enterprise Edition,企业版),用来开发企业环境下的应用程序,通常来说,JavaEE包含JSP、Servlet、JDBC、XML等13种技术。用于Web方向的网站开发,(主要从事后台服务器的开发),在服务器领域,Java是当之无愧的龙头老大。Java学习中,后续会重点学习这部分内容。
JavaME(Java Platform Micro Edition,微型版),用于嵌入式消费类电子设备或者小型移动设备的开发。 其中最为主要的还是小型移动设备的开发(手机)。渐渐的没落了,已经被安卓和IOS给替代了。但是,安卓也是可以用Java来开发的。
过去,如果说 JDK 专门针对程序语言 Java 是正确的。然而,Java 7 引入了一种特殊的结构,使得 Groovy、Clojure 或 Kotlin 等外围编程语言更容易编译成 Java 字节码并使用 Java 运行时环境 (JRE) 执行。因此,今天存在的 Java 平台不仅包括 Java,还包括使用 JDK 工具并在 Java 运行时执行的各种其他外围语言。
JDK 组件、工具和实用程序
JDK 的 bin 目录提供了有助于软件开发过程的各种功能和工具。一些更流行的 JDK 实用程序包括:javac:此实用程序用于将 Java 源代码编译为 Java 字节码。rmic:此实用程序创建用于远程方法调用 (RMI) 的骨架和存根。jar:此压缩实用程序将大量文件聚合到单个 Java ARchive (JAR) 文件中。jar 实用程序使用所有最常见的 zip 实用程序都使用的标准压缩算法。javadoc:此实用程序可以检查类的名称和包含在类中的方法,以及使用特殊注释来为 Java 代码创建应用程序编程接口 (API) 文档。wsgen:这会生成 Java API for XML Web Services (JAX-WS) 所需的各种工件。javap:此实用程序反汇编类文件,生成有关给定编译组件的方法、属性和属性的信息。JDK 还包含许多用于检查 JVM 运行时行为的工具,包括 Java Mission Control (JMC)、Java Flight Recorder (JFR) 和 VisualVM。
四、集成开发环境IntelliJ IDEA
【IDEA的ultimate(最终版)与community(社区版)的区别】
IDEA 全称 IntelliJ IDEA,是java编程语言的集成开发环境。
(1)community(社区版):免费的IntelliJ IDEA community版本是基于开源代码构建的,可以用于纯JVM 和 Android 开发,拥有大部分开发中所需要的功能,但是不能够提供前端css和js的技术支持。
(2)ultimate(最终版):付费的 IntelliJ IDEA ultimate版本可以支持web端和企业端的开发使用,能支持众多前端和后端框架和技术,可以提供分析和数据库工具、HTTP客户端,允许免费使用30天(①购买正版;②可每30天卸载重新安装哦;)
这里我选择的是IntelliJ IDEA Ultimate,在下面网址下载即可使用,无需安装。
Download IntelliJ IDEA – The Leading Java and Kotlin IDE (jetbrains.com)
环境变量
开发Java程序,需要使用JDK提供的开发工具(比如javac.exe、java.exe等命令),而这些工具在JDK的安装目录的bin目录下,如果不配置环境变量,那么这些命令只可以在bin目录下使用,而我们想要在任意目录下都能使用,所以就要配置环境变量。注意:现在最新从官网上下载的JDK安装时会自动配置javac、java命令的路径到Path环境变量中去 ,所以javac、java可以直接使用。如果下载的是IntelliJ IDEA Ultimate,那么下载即可使用,无需安装,也无需配置环境变量。
第二课-----Java基础语法
一、注释
注释是对代码的解释和说明文字。Java中的注释分为三种:
单行注释:
//内容
多行注释:
/*
内容1
内容2
*/
注意:多行注释不能嵌套使用。
* 文档注释:
/**
内容1
内容2
*/
文档注释用于生成API说明文档。
使用技巧
如果我们要对代码进行解释,那么就可以使用注释。 当注释的内容比较少,一行就写完了,可以用单行注释。 如果注释的内容比较多,需要写在多行,那么可以使用多行注释。
注意点
注释的内容不会参与编译和运行的,仅仅是对代码的解释说明而已。所以,不管在注释当中写什么内容,都不会影响代码运行的结果。
二、关键字
被Java赋予了特定含义的英文单词。当我们在代码中写了关键字之后,程序在运行的时候,就知道要做什么事情了。注意:关键字很多,不用刻意去记。
第一个关键字class,表示定义一个类。类:Java项目最基本的组成单元,一个完整的Java项目有可能会有成千上万个类来组成的。class后面跟随的就是这个类的名字,简称:类名。在类名后面会有一对大括号,表示这个类的内容。举例:
public class demo{
}
解释:class表示定义类。
类名:HelloWorld, demo后面的大括号表示这个类的范围。
三、字面量
作用:告诉程序员,数据在程序中的书写格式。
区分技巧
1. 不带小数点的数字都是整数类型的字面量。
2. 只要带了小数点,那么就是小数类型的字面量。
3. 只要用双引号引起来的,不管里面的内容是什么,不管里面有没有内容,都是字符串类型的字面量。
4. 字符类型的字面量必须用单引号引起来,不管内容是什么,但是个数有且只能有一个。
5. 字符类型的字面量只有两个值,true、false。
6. 空类型的字面量只有一个值,null。
四、变量
变量就在程序中临时存储数据的容器。但是这个容器中只能存一个值。
变量的定义格式: 数据类型 变量名 = 数据值;
变量名:其实就是这个容器的名字。当以后想要使用变量里面的数据时,直接使用变量名就可以了。
数据值:真正存储在容器中的数据。
分号:表示语句的结束,就跟以前写作文时候的句号是一样的。
变量的注意事项
- 变量名不能重复
- 在一条语句中,可以定义多个变量。但是这种方式影响代码的阅读,所以了解一下即可。
- 变量在使用之前必须要赋值。
五、Java语言数据类型的分类
1.基本数据类型
基本数据类型的四类八种
注意
- - 在java中整数默认是int类型,浮点数默认是double类型。
- - 如果要定义 一个整数类型的变量,不知道选择哪种数据类型了,默认使用int。
- - 如果要定义 一个小数类型的变量,不知道选择哪种数据类型了,默认使用double。
- - 如果要定义一个long类型的变量,那么在数据值的后面需要加上L后缀。(大小写都可以,建议大写。)
- - 如果要定义一个float类型的变量,那么在数据值的后面需要加上F后缀。(大小写都可以)
2.引用数据类型
用户自定义的类型。
六、标识符
业内大多数程序员都在遵守阿里巴巴的命名规则。
硬性要求:必须要这么做,否则代码会报错。
- - 必须由数字、字母、下划线_、美元符号$组成。
- - 数字不能开头
- - 不能是关键字
- - 区分大小写的。
软件建议:如果不这么做,代码不会报错,但是会让代码显得比较low。
1.小驼峰命名法,适用于变量名和方法名
- * 如果是一个单词,那么全部小写,比如:name
- * 如果是多个单词,那么从第二个单词开始,首字母大写,比如:firstName、maxAge
2.大驼峰命名法,适用于类名
- * 如果是一个单词,那么首字母大写。比如:Demo、Test。
- * 如果是多个单词,那么每一个单词首字母都需要大写。比如:HelloWorld
3.不管起什么名字,都要做到见名知意。
阿里巴巴命名规范细节:
(1). 尽量不要用拼音。但是一些国际通用的拼音可视为英文单词。
正确:alibaba、hangzhou、nanjing
错误:jiage、dazhe
(2). 平时在给变量名、方法名、类名起名字的时候,不要使用下划线或美元符号。
错误:_name
正确:name
第三课-----运算符与表达式
运算符:就是对常量或者变量进行操作的符号。比如: + - * /
表达式:用运算符把常量或者变量连接起来的,符合Java语法的式子就是表达式。比如:a + b 这个整体就是表达式。而其中+是算术运算符的一种,所以这个表达式也称之为算术表达式。
一、算术运算符:+ - * / %
运算特点:+ - * / 跟小学数学中一模一样没有任何区别.。
注意:
- 1.整数相除结果只能得到整除,如果结果想要是小数,必须要有小数参数。
- 2.小数直接参与运算,得到的结果有可能是不精确的。
案例:
System.out.println( 10 / 3);//3
System.out.println(10.0 / 3);//3.3333333333333335
%:取模、取余。
他做的也是除法运算,只不过获取的是余数而已。
案例:
System.out.println(10 % 2);//0
System.out.println(10 % 3);//1
隐式转换:也叫自动类型提升。就是把一个取值范围小的数据或者变量,赋值给另一个取值范围大的变量。此时不需要我们额外写代码单独实现,是程序自动帮我们完成的。
两种提升规则:
- * 取值范围小的,和取值范围大的进行运算,小的会先提升为大的,再进行运算。
- * byte、short、char三种类型的数据在运算的时候,都会直接先提升为int,然后再进行运算。
强制转换:如果要把一个取值范围大的数据或者变量赋值给另一个取值范围小的变量。是不允许直接操作。如果一定要这么干,就需要加入强制转换。
书写格式:目标数据类型 变量名 = (目标数据类型)被强转的数据;
注意点:
强制转换有可能会导致数据发生错误。(数据的精度丢失)
二、字符串的+操作
核心技巧:
- 当+操作中出现字符串时,此时就是字符串的连接符,会将前后的数据进行拼接,并产生一个新的字符串。
- 当连续进行+操作时,从左到右逐个执行的。
字符的+操作
规则: 当+操作中出现了字符,会拿着字符到计算机内置的ASCII码表中去查对应的数字,然后再进行计算。
案例:
char c = 'a';
int result = c + 0;
System.out.println(result);//97
三、自增自减运算符
++ 自增运算符 ,-- 自减运算符
使用方式:
- ++放在变量的前面,先自增后参与运算。 比如:++a*3
- ++放在变量的后面,先参与运算后自增。 比如:3*a++
注意点:
不管是先++,还是后++。单独写在一行的时候,运算结果是一模一样的。
四、扩展赋值运算符
分类:+=、-=、*=、/=、%=
运算规则: 就是把左边跟右边进行运算,把最终的结果赋值给左边,对右边没有任何影响。
例如:a+=b;等价:a =(对应的强制转换的类型)a + b;
注意点:
扩展的赋值运算符中隐层还包含了一个强制转换。
五、关系运算符
又叫比较运算符,其实就是拿着左边跟右边进行了判断而已。
分类:
| 符号 | 解释 |
| ---- | ------------------------------------------------------------ |
| == | 就是判断左边跟右边是否相等,如果成立就是true,如果不成立就是false |
| != | 就是判断左边跟右边是否不相等,如果成立就是true,如果不成立就是false |
| > | 就是判断左边是否大于右边,如果成立就是true,如果不成立就是false |
| >= | 就是判断左边是否大于等于右边,如果成立就是true,如果不成立就是false |
| < | 就是判断左边是否小于右边,如果成立就是true,如果不成立就是false |
| <= | 就是判断左边是否小于等于右边,如果成立就是true,如果不成立就是false |
### 注意点:
* 关系运算符最终的结果一定是布尔类型的。要么是true,要么是false
* 在写==的时候,千万不要写成=
六、逻辑运算符
&:逻辑与(而且)
两边都为真,结果才是真,只要有一个为假,那么结果就是假。
|:逻辑或(或者)
两边都为假,结果才是假,只要有一个为真,那么结果就是真。
^(异或)的使用:
两边相同,结果为false,如果两边不同,结果为true
!(取反)的使用: 是取反,也叫做非。
false取反就是true,true取反就是false
温馨提示:**取反最多只用一个。**
七、短路逻辑运算符
&&: 运算结果跟&是一模一样的,只不过具有短路效果。
||:运算结果跟|是一模一样的。只不过具有短路效果。
逻辑核心:
- 当左边不能确定整个表达式的结果,右边才会执行。
- 当左边能确定整个表达式的结果,那么右边就不会执行了。从而提高了代码的运行效率。
八、三元运算符
又叫做:三元表达式或者问号冒号表达式。
格式:关系表达式 ? 表达式1 :表达式2 ;
计算规则:
- * 计算关系表达式的值。
- * 如果关系表达式的值为真,那么执行表达式1。
- * 如果关系表达式的值为假,那么执行表达式2。
注意点:
三元运算符的最终结果一定要被使用,要么赋值给一个变量,要么直接打印出来。
第四课-----流程控制语句
在一个程序执行的过程中,各条语句的执行顺序对程序的结果是有直接影响的。所以,我们必须清楚每条语句的执行流程。而且,很多时候要通过控制语句的执行顺序来实现我们想要的功能。
流程控制语句分类
- 顺序结构
- 判断和选择结构(if, switch)
- 循环结构(for, while, do…while)
一、 顺序结构
顺序结构是程序中最简单最基本的流程控制,没有特定的语法结构,按照代码的先后顺序,依次执行,程序中大多数的代码都是这样执行的。
二、判断语句:if语句
格式1:
if (关系表达式) {
语句体;
}
执行流程:
- 首先计算关系表达式的值
- 如果关系表达式的值为true就执行语句体
- 如果关系表达式的值为false就不执行语句体
- 继续执行后面的语句内容
第一种格式的细节:
- 如果我们要对一个布尔类型的变量进行判断,不要写==,直接把变量写在小括号中即可。
- 如果大括号中的语句体只有一条,那么大括号可以省略不写
- 如果大括号省略了,那么if只能控制距离他最近的那一条语句。
**建议:**自己不要去写,如果别人这么写了,你要能看懂即可。
格式2:
if (关系表达式) {
语句体1;
} else {
语句体2;
}
执行流程:
- 首先计算关系表达式的值
- 如果关系表达式的值为true就执行语句体1
- 如果关系表达式的值为false就执行语句体2
- 继续执行后面的语句内容
格式3:
if (关系表达式1) {
语句体1;
} else if (关系表达式2) {
语句体2;
}
...
else {
语句体n+1;
}
执行流程:
首先计算关系表达式1的值
- 如果值为true就执行语句体1;如果值为false就计算关系表达式2的值
- 如果值为true就执行语句体2;如果值为false就计算关系表达式3的值
- …
- 如果没有任何关系表达式为true,就执行语句体n+1。
三、switch语句
格式:
switch (表达式) {
case 1:
语句体1;
break;
case 2:
语句体2;
break;
...
default:
语句体n+1;
break;
}
执行流程:
- 首先计算出表达式的值
- 其次,和case依次比较,一旦有对应的值,就会执行相应的语句,在执行的过程中,遇到break就会结束。
- 最后,如果所有的case都和表达式的值不匹配,就会执行default语句体部分,然后程序结束掉。
switch的扩展知识:
- default可以放在任意位置,也可以省略
- case穿透,不写break会引发case穿透现象
switch在JDK12的新特性:
int number = 10;
switch (number) {
case 1 -> System.out.println("一");
case 2 -> System.out.println("二");
case 3 -> System.out.println("三");
default -> System.out.println("其他");
}
switch和if第三种格式各自的使用场景
- 当我们需要对一个范围进行判断的时候,用if的第三种格式
- 当我们把有限个数据列举出来,选择其中一个执行的时候,用switch语句
四、循环结构
for循环结构
循环语句可以在满足循环条件的情况下,反复执行某一段代码,这段被重复执行的代码被称为循环体语句,当反复 执行这个循环体时,需要在合适的时候把循环判断条件修改为false,从而结束循环,否则循环将一直执行下去,形 成死循环。
for循环格式:
for (初始化语句;条件判断语句;条件控制语句) {
循环体语句;
}
格式解释:
- - 初始化语句: 用于表示循环开启时的起始状态,简单说就是循环开始的时候什么样
- - 条件判断语句:用于表示循环反复执行的条件,简单说就是判断循环是否能一直执行下去
- - 循环体语句: 用于表示循环反复执行的内容,简单说就是循环反复执行的事情
- - 条件控制语句:用于表示循环执行中每次变化的内容,简单说就是控制循环是否能执行下去
执行流程:
- ①执行初始化语句
- ②执行条件判断语句,看其结果是true还是false
- 如果是false,循环结束
- 如果是true,继续执行
- ③执行循环体语句
- ④执行条件控制语句
- ⑤回到②继续
for循环书写技巧:
- - 确定循环的开始条件
- - 确定循环的结束条件
- - 确定循环要重复执行的代码
while循环
格式:
初始化语句;
while(条件判断语句){
循环体;
条件控制语句;
}
do...while循环
格式:
初始化语句;
do{
循环体;
条件控制语句;
}while(条件判断语句);
特点:
先执行,再判断。
三种格式的区别:
- for和while循环,是先判断,再执行。
- do...while是先执行,再判断。
- 当知道循环次数或者循环范围的时候,用for循环。
- 当不知道循环次数,也不知道循环范围,但是知道循环的结束条件时,用while循环。
无限循环
又叫死循环。循环一直停不下来。
for格式:
for(;;){
System.out.println("循环执行一直在打印内容");
}
while格式:
while(true){
System.out.println("循环执行一直在打印内容");
}
do...while格式:
do{
System.out.println("循环执行一直在打印内容");
}while(true);
无限循环的注意事项:
- 最为常用的格式:while
- 无限循环下面不能再写其他代码了,因为永远执行不到。
条件控制语句
* break
* continue
- break:不能单独存在的。可以用在switch和循环中,表示结束,跳出的意思。
- continue:不能单独存在的。只能存在于循环当中。表示:跳过本次循环,继续执行下次循环。
break 标签
break只能跳出1层循环,如果想跳出多层循环的话可以使用break 标签名;的形式。
例如:
t1:for(){
for(){
break t1;
}
}
第五课-----数组
数组概念:指的是一种容器,可以同来存储同种数据类型的多个值。但是数组容器在存储数据的时候,需要结合隐式转换考虑。比如,定义了一个int类型的数组。那么boolean。double类型的数据是不能存到这个数组中的,但是byte类型,short类型,int类型的数据是可以存到这个数组里面的。
建议:容器的类型,和存储的数据类型保持一致。
一、数组的定义
格式一:数据类型 [] 数组名
比如:int [] array
格式二:
数据类型 数组名 []
比如: int array []
详解:
- 数据类型:限定了数组以后能存什么类型的数据。
- 方括号:表示现在定义的是一个数组。
- 数组名:就是一个名字而已,方便以后使用。
注意点:
- 方法括号跟数组名,谁写在前面,谁写在后面都是一样的。
- 平时习惯性使用第一种方式。
二、数组的静态初始化
完整格式:
数据类型[] 数组名 = new 数据类型[]{元素1,元素2,元素3,元素4...};
比如:
int[] arr = new int[]{11,22,33};
double[] arr = new double[]{1.1,1.2,1.3};
格式详解:
- 数据类型:限定了数组以后能存什么类型的数据。
- 方括号:表示现在定义的是一个数组。
- 数组名:其实就是名字而已,方便以后使用,在起名字的时候遵循小驼峰命名法。
- new:就是给数组在内存中开辟了一个空间。
- 数据类型:限定了数组以后能存什么类型的数据。前面和后面的数据类型一定要保持一致。
- 大括号:表示数组里面的元素。元素也就是存入到数组中的数据。多个元素之间,一定要用逗号隔开。
注意点:
- 等号前后的数据类型必须保持一致。
- 数组一旦创建之后,长度不能发生变化。
简化格式:
数据类型[] 数组名 = {元素1,元素2,元素3,元素4...};
三、数组的地址值
打印数组名字的时候,实际出现的是数组的地址值。数组的地址值:就表示数组在内存中的位置。
以[I@6d03e736为例:
- [ :表示现在打印的是一个数组。
- I:表示现在打印的数组是int类型的。
- @:仅仅是一个间隔符号而已。
- 6d03e736:就是数组在内存中真正的地址值。(十六进制的)
但是,我们习惯性会把[I@6d03e736这个整体称之为数组的地址值。
地址值对于我们来京,作用不大,简单了解。
四、数组元素访问
格式:数组名[索引];
作用:
- 获取数组中对应索引上的值
- 修改数组中对应索引上的值
一旦修改之后,原来的值就会被覆盖了。
索引也叫角标、下标,就是数组容器中每一个小格子对应的编号。
索引的特点:
- 索引一定是从0开始的。
- 连续不间断。
- 逐个+1增长。
数组的遍历
遍历:就是把数组里面所有的内容一个一个全部取出来。
数组的长度:数组名.length;
通用代码:
for(int i = 0; i < arr.length; i++){
//在循环的过程中,i依次表示数组中的每一个索引
sout(arr[i]);//就可以把数组里面的每一个元素都获取出来,并打印在控制台上了。
}
五、数组的动态初始化
格式:数据类型[] 数组名 = new 数据类型[数组的长度];
数组的默认初始化值:
- 整数类型:0
- 小数类型:0.0
- 布尔类型:false
- 字符类型:'\u0000'
- 引用类型:null
数组两种初始化方式的区别
静态初始化:int[] arr = {1,2,3,4,5};
动态初始化:int[] arr = new int[3];
静态初始化:手动指定数组的元素,系统会根据元素的个数,计算出数组的长度。
动态初始化:手动指定数组长度,由系统给出默认初始化值。
使用场景:
- 只明确元素个数,但是不明确具体的数据,推荐使用动态初始化。
- 已经明确了要操作的所有数据,推荐使用静态初始化。
第六课-----方法
一、 方法的概念
方法(method)是程序中最小的执行单元
* 注意:
- 方法必须先创建才可以使用,该过程成为方法定义
- 方法创建后并不是直接可以运行的,需要手动使用后,才执行,该过程成为方法调用
二、方法的定义和调用
无参数方法定义和调用
定义格式:
public static void 方法名 ( ) {
// 方法体;
}
调用格式:方法名();
注意:方法必须先定义,后调用,否则程序将报错
带参数方法定义和调用
定义格式:
参数:由数据类型和变量名组成 - 数据类型 变量名
参数范例:int a
public static void 方法名 (参数1) {
方法体;
}
public static void 方法名 (参数1, 参数2, 参数3...) {
方法体;
}
* 范例:
public static void isEvenNumber(int number){
}
public static void getMax(int num1, int num2){
}
* 注意:
- 方法定义时,参数中的数据类型与变量名都不能缺少,缺少任意一个程序将报错
- 方法定义时,多个参数之间使用逗号分隔
* 调用格式:
方法名(参数);
方法名(参数1,参数2);
* 范例:
isEvenNumber(10);
getMax(10,20);
* 方法调用时,参数的数量与类型必须与方法定义中的设置相匹配,否则程序将报错
形参和实参
1. 形参:方法定义中的参数
等同于变量定义格式,例如:int number
2. 实参:方法调用中的参数
等同于使用变量或常量,例如: 10 number
三、带返回值方法定义和调用
* 定义格式
public static 数据类型 方法名 ( 参数 ) {
return 数据 ;
}
* 范例
public static boolean isEvenNumber( int number ) {
return true ;
}
public static int getMax( int a, int b ) {
return 100 ;
}
* 注意:
* 方法定义时return后面的返回值与方法定义上的数据类型要匹配,否则程序将报错
* 调用格式
方法名 ( 参数 ) ;
数据类型 变量名 = 方法名 ( 参数 ) ;
* 范例
isEvenNumber ( 5 ) ;
boolean flag = isEvenNumber ( 5 );
* 注意:方法的返回值通常会使用变量接收,否则该返回值将无意义
四、方法的注意事项
- 方法不能嵌套定义
- void表示无返回值,可以省略return,也可以单独的书写return,后面不加数据
方法的通用格式
* 格式:
public static 返回值类型 方法名(参数) {
方法体;
return 数据 ;
}
* 解释:
- public static 修饰符,目前先记住这个格式
- 返回值类型 方法操作完毕之后返回的数据的数据类型
- 如果方法操作完毕,没有数据返回,这里写void,而且方法体中一般不写return
- 方法名 调用方法时候使用的标识
- 参数 由数据类型和变量名组成,多个参数之间用逗号隔开
- 方法体 完成功能的代码块
- return 如果方法操作完毕,有数据返回,用于把数据返回给调用者
* 定义方法时,要做到两个明确
- 明确返回值类型:主要是明确方法操作完毕之后是否有数据返回,如果没有,写void;如果有,写对应的数据类型
- 明确参数:主要是明确参数的类型和数量
* 调用方法时的注意:
- void类型的方法,直接调用即可
- 非void类型的方法,推荐用变量接收调用
五、方法重载
方法重载指同一个类中定义的多个方法之间的关系,满足下列条件的多个方法相互构成重载
- 多个方法在同一个类中
- 多个方法具有相同的方法名
- 多个方法的参数不相同,类型不同或者数量不同
* 注意:
- 重载仅对应方法的定义,与方法的调用无关,调用方式参照标准格式
- 重载仅针对同一个类中方法的名称与参数进行识别,与返回值无关,换句话说不能通过返回值来判定两个方法是否相互构成重载
第七课-----面向对象
一、类和对象
类和对象的理解:
- 客观存在的事物皆为对象 ,所以我们也常常说万物皆对象。
- 类是对现实生活中一类具有共同属性和行为的事物的抽象
- 类是对象的数据类型,类是具有相同属性和行为的一组对象的集合
- 简单理解:类就是对现实事物的一种描述
类的组成
- 属性:指事物的特征,例如:手机事物(品牌,价格,尺寸)
- 行为:指事物能执行的操作,例如:手机事物(打电话,发短信)
* 类和对象的关系
- 类:类是对现实生活中一类具有共同属性和行为的事物的抽象
- 对象:是能够看得到摸的着的真实存在的实体
* 简单理解:**类是对事物的一种描述,对象则为具体存在的事物**
二、类的定义
类的组成是由属性和行为两部分组成
- 属性:在类中通过成员变量来体现(类中方法外的变量)
- 行为:在类中通过成员方法来体现(和前面的方法相比去掉static关键字即可)
类的定义步骤:
①定义类
②编写类的成员变量
③编写类的成员方法
格式:
public class 类名 {
// 成员变量
变量1的数据类型 变量1;
变量2的数据类型 变量2;
…
// 成员方法
方法1;
方法2;
}
示例代码:
public class Phone {
//成员变量
String brand;
int price;
//成员方法
public void call() {
System.out.println("打电话");
}
public void sendMessage() {
System.out.println("发短信");
}
}
三、对象的使用
创建对象的格式:类名 对象名 = new 类名();
调用成员的格式:
- 对象名.成员变量
- 对象名.成员方法();
* 示例代码
创建对象
格式:类名 对象名 = new 类名();
范例:Phone p = new Phone();
使用对象
1:使用成员变量
格式:对象名.变量名
范例:p.brand
2:使用成员方法
格式:对象名.方法名()
范例:p.call()
public class PhoneDemo {
public static void main(String[] args) {
//创建对象
Phone p = new Phone();
//使用成员变量
System.out.println(p.brand);
System.out.println(p.price);
p.brand = "小米";
p.price = 2999;
System.out.println(p.brand);
System.out.println(p.price);
//使用成员方法
p.call();
p.sendMessage();
}
}
四、 对象内存图
示例代码:
class Emp{
public int age;
}
public class test1 {
public static void change(Emp emp){
emp.age=50;
emp=new Emp();
emp.age=100;
}
public static void main(String[] args) {
Emp emp =new Emp();
emp.age=100;
System.out.println(emp.age);
change(emp);
System.out.println(emp.age);
}
}
内存图:
程序运行过程:
程序启动后,jvm启动时首先将加载系统类例如:Object然后加载main方法所在的测试类Test的字节码信息到方法区。
接着main方法入栈,由于要创建Emp的对象,所以类Emp的字节码信息会加载到方法区。再根据方法区中Emp的类结构信息在堆区开辟一个空间存储要创建的Emp对象的属性和方法。Emp类对象的age属性默认值为0,由于age没有显示初始化、Emp类没有有参构造和显示声明的无参构造,jvm将调用Emp的默认构造方法,结果age值不变,还是为0。最后将该空间的地址(假设是0x001f)赋给Emp创建的变量emp,使该变量指向该空间。
然后给emp.age赋值100,目前emp指向的是0x001f空间,所以就是给0x001f空间的age变量赋值100。打印输出emp.age的值。接着调用静态方法change(emp),change方法入栈传递实参emp给形参emp。然后将50赋给emp.age,0x001f空间的age值变为50。
接着再根据方法区中Emp的类结构信息再在堆区开辟一个空间存储新创建的Emp对象的属性和方法。其他步骤同上,最后将该空间的地址(假设是0x002f)赋给变量emp,使该变量指向该空间。然后给emp.age赋值100,目前emp指向的是0x002f空间,所以就是给0x002f空间的age变量赋值100。然后change方法change方法出栈,0x002f空间将被回收。
程序返回main方法,接着输出打印emp.age的值,也就是0x001f空间的age的值50。main方法出栈,程序结束。
输出结果:
100
50
总结:
多个对象在堆内存中,都有不同的内存划分,成员变量存储在各自的内存区域中,成员方法多个对象共用的一份
五、成员变量和局部变量
成员变量和局部变量的区别
- 类中位置不同:成员变量(类中方法外)局部变量(方法内部或方法声明上)
- 内存中位置不同:成员变量(堆内存)局部变量(栈内存)
- 生命周期不同:成员变量(随着对象的存在而存在,随着对象的消失而消失)局部变量(随着方法的调用而存在,醉着方法的调用完毕而消失)
- 初始化值不同:成员变量(有默认初始化值)局部变量(没有默认初始化值,必须先定义,赋值才能使用)
六、封装
封装是面向对象三大特征之一(封装,继承,多态),对象代表什么,就得封装对应的数据,并提供数据对应的行为。
封装代码实现
将类的某些信息隐藏在类内部,不允许外部程序直接访问,而是通过该类提供的方法来实现对隐藏信息的操作和访问,成员变量private,提供对应的getXxx()/setXxx()方法。
private关键字
private是一个修饰符,可以用来修饰成员(成员变量,成员方法,被private修饰的成员,只能在本类进行访问,针对private修饰的成员变量,如果需要被其他类使用,提供相应的操作。
- 提供“get变量名()”方法,用于获取成员变量的值,方法用public修饰
- 提供“set变量名(参数)”方法,用于设置成员变量的值,方法用public修饰
示例代码:
class Student {
//成员变量
String name;
private int age;
//提供get/set方法
public void setAge(int a) {
if(a<0 || a>120) {
System.out.println("你给的年龄有误");
} else {
age = a;
}
}
public int getAge() {
return age;
}
//成员方法
public void show() {
System.out.println(name + "," + age);
}
}
/*
学生测试类
*/
public class StudentDemo {
public static void main(String[] args) {
//创建对象
Student s = new Student();
//给成员变量赋值
s.name = "林青霞";
s.setAge(30);
//调用show方法
s.show();
}
}
七、this关键字
在方法中,当局部变量与成员变量同名,可以使用this关键字修饰,带this修饰的变量指的是成员变量,不带是局部变量。
public class Student {
private String name;
private int age;
public void setName(String name) {
this.name = name;
}
}
注意:
- this修饰的变量用于指代成员变量,其主要作用是(区分局部变量和成员变量的重名问题)
- 方法的形参如果与成员变量同名,不带this修饰的变量指的是形参,而不是成员变量
- 方法的形参没有与成员变量同名,不带this修饰的变量指的是成员变量
八、构造方法
构造方法是一种特殊的方法,作用:创建对象 Student stu = new Student();
* 格式:
public class 类名{
修饰符 类名( 参数 ) {
}
}
* 功能:主要是完成对象数据的初始化
* 示例代码:
class Student {
private String name;
private int age;
//构造方法
public Student() {
System.out.println("无参构造方法");
}
public void show() {
System.out.println(name + "," + age);
}
}
/*
测试类
*/
public class StudentDemo {
public static void main(String[] args) {
//创建对象
Student s = new Student();
s.show();
}
}
构造方法的注意事项
* 构造方法的创建
- 如果没有定义构造方法,系统将给出一个默认的无参数构造方法
- 如果定义了构造方法,系统将不再提供默认的构造方法
* 构造方法的重载
如果自定义了带参构造方法,还要使用无参数构造方法,就必须再写一个无参数构造方法
* 推荐的使用方式
无论是否使用,都手工书写无参数构造方法
* 重要功能!
可以使用带参构造,为成员变量进行初始化
标准类制作
① 类名需要见名知意
② 成员变量使用private修饰
③ 提供至少两个构造方法,无参构造方法,带全部参数的构造方法
④ get和set方法,提供每一个成员变量对应的setXxx()/getXxx()
⑤ 如果还有其他行为,也需要写上
创建对象并为其成员变量赋值的两种方式
- 无参构造方法创建对象后使用setXxx()赋值
- 使用带参构造方法直接创建带有属性值的对象