Java基础知识点梳理

Java基础知识点梳理

摘要:
虽然已经在实际工作中经常与java打交道,但是一直没系统地对java这门语言进行梳理和总结,掌握的知识也比较零散。恰好利用这段时间重新认识下java,并对一些常见的语法和知识点做个总结与回顾,一方面为了加深印象,方便后面查阅,一方面为了学好java打下基础。

Java简介

java语言于1995年正式推出,最开始被命名为Oak语言,由James Gosling(詹姆斯·高斯林)在Sun Microsystems公司和同事共同研发,Microsystems如今已经被oracle收购。java语言具有以下特点:

  • 简单性
  • 面向对象
  • 可移植性
  • 安全性
  • 健壮性
  • 多线程

Java文件运行过程如下:

  1. 编写源代码,文件格式: .java
  2. 编译 .java文件 生成.class文件(二进制字节码文件)
  3. 运行 .class文件在JVM上(java虚拟机,支持多平台)

Java语言基础语法

注释

注释用于解释程序,增强可读性,java中注释有以下几种:

  1. 单行注释,语法如下:
// 单行注释
  1. 多行注释,语法如下:
/*
多行注释
多行注释
*/
  1. javadoc注释,是一种专业注释,可以被javadoc.exe工具解析提取生成帮助文档
/**
 * javadoc注释
*/

标识符

标识符用于标识类名,方法名,变量名,接口名等,命名需要满足以下规则:

  • 只能由"数字,字母(A-Z 或者 a-z),美元符($)、或者下划线(_)"组成
  • 所有的标识符都应该以字母(A-Z 或者 a-z),美元符($)、或者下划线(_)开始
  • 严格区分大小写,不能用关键字做标识符

java编程规范建议遵守驼峰命名法,类名和接口名首字母大写,变量和方法名首字母小写。Java采用unicode的编码方式,所以标识符也支持中文。

类的定义

java定义一个类用class关键字,有以下几点需要注意:

  • 一个java源文件定义公开的类只能有一个,类名称必须和java源文件名称一致
  • 一个java源文件可以编写多个class
  • 每一个class都可以编写main方法

Java数据类型

基本数据类型

数据类型的作用是指导JVM在运行程序的时候给该数据分配多大的内存空间,Java提供了以下八种基础数据类型:

序号 分类 类型 介绍 实例
01 整数型 byte 8位有符号整数(取值范围:-128~127) byte a = 128;
02 整数型 short 16位有符号整数(取值范围:-32768~32767) short num = 1314;
03 整数型 int 32位有符号整数 int n = 131400;
04 整数型 long 64位有符号整数 long sum = 10000L;
05 浮点型 float 单精度、32位、符合IEEE 754标准的浮点数 float f1 = 13.14f;
06 浮点型 double 双精度、64 位、符合IEEE 754标准的浮点数 double d1 = 13.1452;
07 布尔型 boolean 一位用于表示真假,只能取true 和 false; boolean isMan = true;
08 字符型 char 一个单一的 16 位 Unicode 字符(0~65535) char firstLetter = ‘a’;
整型表示方式

整型有三种表示方式,默认是十进制:

进制 表示方式 实例
十进制 默认的表示方式,以非零数字开始 int x = 10; // x = 10
八进制 以数字零"0"开始 int x = 010; // x = 8
十六进制 以"0x"开始 int x = 0x10; // x = 16
类型转换

类型转换有如下规则:

  1. 八种基本数据类型除了布尔类型之外,剩下的7种类型都可以互相转换
  2. 小容量向大容量转换,可以自动进行,容量从小到大排序为:
    byte < short < int < long < float < double
  3. 大容量数据转换成小容量,需要进行强制类型转换,强转会损失精度
  4. byte, short ,char 混合运算,各自转换成int;多种数据类型混合运算,转换成容量最大的类型再运算。

对于强制类型转换,将long强转成int的语法如下:

long k = 6475201314L;
int num = (int) k;

注意:大容量转换成小容量编译无法通过,比如下面代码无法编译:

byte b = 19;
b = b + 13; // 相当于直接把整型赋值给byte型,报错
b += 13; // 可以编译,等同于 b = (byte)(b + 13)

复合数据类型

字符串(String)

在Java中使用String 类来创建和操作字符串,初始化一个String的语法如下:

// 常用,用双引号直接创建
String testStr = "Wasting time is robbing oneself";
// 不常用,使用char数组创建
char[] helloArray = {'h', 'e', 'l', 'l', 'o'};
String helloString = new String(helloArray);  

由于字符串使用非常频繁,String类也提供了很多方法,下面介绍一些用的比较多的。

  • 对字符串进行修改的常用方法有(包括格式化,大小写转换):
序号 方法 描述
01 String trim() 返回字符串的副本,忽略前面空白和尾部空白。
02 String intern() 返回字符串对象的规范化表示形式。
03 String toUpperCase() 使用默认语言环境的规则将此 String 中的所有字符都转换为大写。
04 String toUpperCase(Locale locale) 使用给定的Locale规则将String中所有字符转换为大写。
05 String toLowerCase() 使用默认语言环境的规则将此 String 中的所有字符都转换为小写。
06 String toLowerCase(Locale locale) 使用给定 Locale 的规则将此 String 中的所有字符都转换为小写。
  • 对字符串进行查找和替换的方法有:
序号 方法 描述
01 boolean startsWith(String str1) 字符串是否以指定的字符串str1开始。
02 boolean startsWith(String str1, int toffset) 字符串指定索引开始的子字符串是否以指定字符串str1开始。
03 boolean endsWith(String str1) 测试此字符串是否以指定的字符串str1结束。
04 int indexOf(String str1) 返回指定子字符串str1在此字符串中第一次出现处的索引。
05 int indexOf(String str1, int fromIndex) 从指定的索引开始,返回指定子字符串str1在此字符串中第一次出现处的索引。
06 int lastIndexOf(String str1)) 返回指定子字符串str1在此字符串中最右边出现处的索引。
07 int lastIndexOf(String str1, int fromIndex) 返回指定子字符串在此字符串中最后一次出现处的索引,从指定的索引开始反向搜索
08 boolean matches(String regex) 测试此字符串是否匹配给定的正则表达式
09 String replace(char oldChar, char newChar) 返回一个用 newChar 替换此字符串中出现的所有 oldChar 得到的新字符串。
10 String replaceAll(String regex, String replacement) 使用给定的 replacement 替换此字符串所有匹配给定的正则表达式的子字符串
  • 获取子字符串的常用方法有:
序号 方法 描述
01 String substring(int beginIndex) 返回一个新的从指定索引开始的字符串。
02 String substring(int beginIndex, int endIndex) 返回从索引beginIndex开始到endIndex结束的新的字符串
03 String[] split(String regex) 根据给定正则表达式的匹配拆分此字符串。
04 String[] split(String regex, int limit) 根据匹配给定的正则表达式来拆分此字符串。
  • 对字符串进行比较的方法有:
序号 方法 描述
01 int compareTo(String anotherString) 按字典顺序比较两个字符串,相等时候返回0。
02 int compareToIgnoreCase(String str) 按字典顺序比较两个字符串,不考虑大小写
03 boolean contentEquals(StringBuffer sb) 当且仅当字符串与指定的StringBuffer有相同顺序的字符时候返回真。
04 boolean equals(Object anObject) 将此字符串与指定的对象比较。
05 boolean equalsIgnoreCase(String anotherString) 将此 String 与另一个 String 比较,不考虑大小写。
  • 其他常见的方法比如统计长度,拼接,转换等:
序号 方法 描述
01 int length() 按字典顺序比较两个字符串,相等时候返回返回此字符串的长度。
02 String toString() 转换成String对象
03 String concat(String str) 将指定字符串连接到此字符串的结尾。
04 char[] toCharArray() 将此字符串转换为一个新的字符数组。
05 char charAt(int index) 返回指定索引处的 char 值。
数组

数组可以用于存放固定大小的同类型元素,声明一个数组的语法如下:

变量类型[] 数组名;   

创建数组的语法:

数组名 = new 变量类型[数组大小];
变量类型[] 数组名 = {value0, value1, ..., valuek};

数组的变量类型可以是前面介绍八种基本数据类型以及复合数据类型,“数组名[索引]” 可以访问数组元素,下面是一个操作一维数组例子:

int[] primeNumbers = {2, 3, 5, 7, 11, 13, 17, 19, 23, 29};
for (int num : primeNumbers) {
	System.out.println("num: " + num);
}

操作二维数组的例子如下:

int[][] a = new int[2][3];
a[0][0] = 19;
String[][] s = new String[2][];
s[0] = new String[2]; // 第一个数组长度为2
s[1] = new String[3]; // 第二个数组长度为3
s[0][0] = "Hello";
s[0][1] = "World";

java.util.Arrays类能方便地操作数组,它提供的所有方法都是静态的,比较常见的方法有:

序号 方法 描述
01 public static int binarySearch(Object[] a, Object key) 用二分查找算法在给定数组中搜索给定值的对象(Byte,Int,double等)。前提是数组在调用前必须排序好的。找到了则返回搜索键的索引;否则返回 (-(插入点) - 1)。
02 public static void sort(Object[] a) 对指定对象数组根据其元素的自然顺序进行升序排列。同样的方法适用于所有的其他基本数据类型(Byte,short,Int等)。

使用Arrays的sort方法进行排序的例子如下:

int[] primeNumbers = {7, 11, 5, 2, 3};
Arrays.sort(primeNumbers);
for (int num : primeNumbers) {
	System.out.println("num: " + num);
}
集合

Java语言提供了一个完善的集合框架,主要包括两种类型的容器,一种是集合(Collection),存储一个元素集合,另一种是图(Map),存储键/值对映射
经常用到的集合有:

序号 类型 描述
01 ArrayList 该类实现了List的接口,实现了动态数组,随机访问和遍历元素时,提供更好的性能,插入删除效率低。
02 LinkedList 该类实现了List接口,允许有null(空)元素。主要用于创建链表数据结构,插入删除效率高,查找效率较低。
03 HashSet 该类实现了set接口,不允许出现重复元素,不保证集合中元素的顺序。
04 HashMap HashMap 是一个散列表,它存储的内容是键值对(key-value)映射,具有很快的访问速度

ArrayList提供的常用方法有:

序号 分类 方法 描述
01 增加 boolean add(E object) 向容器中添加指定数据类型的元素
02 增加 boolean addAll([int index], Collection collection) 向容器中指定的位置增加一个集合
03 获取 E get(int location) 获得容器中位置location的元素
04 删除 E remove(int i) 移除下标为i的元素,返回值是删除的数据元素
05 删除 void clear() 清空容器所有元素
06 统计 int size() 获得容器中元素的个数
07 判断 boolean isEmpty() 获得容器中是否有元素
08 修改 E set(int location, E object) 修改容器中指定位置元素的值

下面是操作一个java.util.ArrayList的例子:

ArrayList list = new ArrayList();
list.add(2);
list.add(3);
list.add(5);
for (int i = 0; i<list.size(); i++) {
	System.out.println(list.get(i));
}
		
list.remove(1);
list.set(1, 19);
类型转换方法

关于数据类型,最后再介绍下Java中常见的类型转换方法:

序号 方法 描述 实例
01 String.toCharArray() String类型转换成char数组 String str = “hello word”;char[] nums = str.toCharArray();
02 Integer.parseInt() String类型转换成int类型 String numStr = “1314”;int num = Integer.parseInt(numStr);
03 Double.parseDouble() String类型转换成Double类型 String doubleStr = “13.14”;double d = Double.parseDouble(doubleStr);
04 Integer.toString() int类型转换成String类型 int num = 12;String numStr = Integer.toString(num);
05 Double.toString() Double类型转换成String类型 Double num = 13.14;String numStr = Double.toString(num);

运算符

Java的运算符种类比较多,本文介绍几种常见的运算符:

算术运算符

java的算术运算符如下表(int a = 10; int b= 9;):

序号 操作符 描述 实例
01 + 加法 - 对运算符两侧的值进行相加 a + b = 19;
02 - 减法 - 左操作数减去右操作数 a - b = 1;
03 * 乘法 - 对运算符两侧的值进行乘法运算 a * b = 90;
04 / 除法 - 左操作数除以右操作数 a / b = 1;
05 取余 - 左操作数除以右操作数的余数 a % b = 1;
06 ++ 自增: 操作数的值增加1 ++a,a++均为11,前者先自增,再进行表达式运算,后者顺序相反
07 自减:操作数的值减少1 –b,b-- 均为8,前者先自减,再进行表达式运算,后者顺序相反

基本的赋值运算符"=" 可以与前5种算术运算符组合成 +=,-=,*=,/=,%=等扩展的赋值运算符
int a = 10; a += 5; 等价于 a = (int)(a + 5);
其他的运算符类似,扩展运算符默认有类型转换,但是不改变运算结果类型

对于"+"运算符,只要两边的操作数有一个是字符串就会进行字符串连接运算生成一个新的字符串。

关系运算符

java中主要有以下六种关系运算符:

运算符 描述 运算符 描述 运算符 描述
> 大于 >= 大于等于 < 小于
<= 小于等于 == 等于 != 不等于

关系运算符返回的结果是布尔型

逻辑运算符

主要有以下三种逻辑运算符(boolean a = true; boolean b = false):

序号 操作符 描述 实例
01 && 逻辑与,只有两个操作数都为真才返回true a && b 为false
02 || 逻辑或,两个操作数只要有一个为真就返回true a || b 为true
03 逻辑非,对操作数的状态取反 !a 为false,!b为true

位运算符

位运算符对两个操作数的每一位进行运算,有以下几种常见的类型:

运算符 描述 运算符 描述 运算符 描述
& 按位与 | 按位或 ^ 按位异或
~ 按位取反 <> 按位左移/右移 >>> 指定位数右移,空位补零

三目运算符

三目元素符的语法规则:

布尔表达式 ? 表达式1 : 表达式2;

布尔表达式为真执行表达式1,为假执行表达式2,利用三目运算符求最大值的一个例子如下:

int a = 10;
int b = 9;
int max = (a > b) ? a : b;
System.out.println("max number is: " + max);

控制语句

每种编程语言都少不了控制语句来控制代码流程,java语言也提供了丰富的控制语句。

选择结构

if语句

if语句常见的语法:

// 第一种写法,else分支可以省略
if (布尔表达式) {
	表达式为真要执行的语句;
} else {
	其他条件要执行的语句
}
// 第二种写法,最后的else分支可以省略
if (布尔表达式) {
	表达式为真要执行的语句;
} else if (布尔表达式1) {
	表达式1为真要执行的语句
} else if (布尔表达式2) {
	表达式2为真要执行的语句
} else {
	除上述条件之外要执行的语句
}
switch语句

switch语句的语法如下:

switch (expression) {
    case value1 :
       // 匹配value1成功之后执行的语句
       break; // 可选
    case value2 :
       // 匹配value2成功之后执行的语句
       break; //可选
    ...
    default : // 可选
       // 前面case分支都没匹配时执行的语句
}

其中expression支持byte、short、int、char以及字符串(String),byte、short、char会转换为int类型。程序只有遇到break语句才会跳出switch语句,缺少break的分支会继续往下面分支执行。

循环结构

程序当中总会有些需要重复执行的代码片段,因此各个编程语言都支持循环语法。

for语句

for语句的语法如下:

for (初始化表达式; 布尔表达式; 更新表达式) {
    // 要重复执行的代码片段
}

执行过程:

  1. 初始化表达式最先执行而且只执行一次;
  2. 判断布尔表达式,如果是真执行循环体,如果是假则退出循环
  3. 循环体执行之后更新表达式,再执行步骤2,反复循环直到退出循环
    利用for循环计算数字1到10的和的代码如下:
int sum = 0;
for (int i = 0; i <= 10; i++) {
	sum += i;
}
System.out.println("the sum is: " + sum);
while语句

while语句的语法如下:

while (布尔表达式) {
  // 循环内容
}

执行过程:
先判断布尔表达式的值,为真就执行循环体,为假则循环结束,循环体可能一次也不执行。
使用while循环计算数字1到10的和是:

int sum = 0;
int i = 0;
while (i <=10) {
	sum += i;
	i++;
}
System.out.println("The sum is: " + sum);
do…while 循环

do…while循环的语法如下:

do {
	// 循环内容
} while (布尔表达式);

do…while循环先执行循环内容再判断表达式,循环体至少会执行一次。

控制循环语句

break语句

break使用在switch语句中终止switch执行,使用在循环语句中终止循环,跳出当前循环体。语法如下:

break;
continue语句

continue表示直接进入下一次循环继续执行,语法如下:

continue;

Java变量类型

在Java中,所有的变量在使用前必须声明。声明变量的基本格式如下:

type identifier = value;

value的数据类型必须和声明的变量类型一致,变量的值可变化,必须先声明再赋值才能访问。

局部变量:

java中的局部变量声明在方法内部,有以下特点:

  • 变量只在作用域内有效,超出作用域变量将会被销毁;
  • 变量是在栈上分配,没有默认值,所以局部变量被声明后,必须经过初始化,才可以使用。

局部变量存储在栈内存中。

实例变量(成员变量):

成员变量在方法体之外声明,有以下特点:

  • 当一个对象被实例化之后,每个实例变量的值就跟着确定
  • 实例变量在对象创建的时候创建,在对象被销毁的时候销毁
  • 实例变量具有默认值,数值型变量的默认值是0,布尔型变量的默认值是false,引用类型变量的默认值是null。

成员变量在JVM的堆内存中存储,垃圾回收器主要针对堆内存处理。

静态变量:

静态变量用static关键字声明,需要记住以下特点:

  • 无论一个类创建了多少个对象,类只拥有静态变量的一份拷贝
  • 静态变量在第一次被访问时创建,在程序结束时销毁。
  • 静态变量具有默认值,取值和实例变量类似

不同类型变量在JVM中的存储情况如下表:

栈内存 堆内存 方法区内存
局部变量/执行的方法 实例变量/new出来的对象 静态变量/代码片段

方法/函数

方法语法

方法实质就是一段可以重复使用,完成某项特定功能的片段,和C语言中的函数类似。方法的语法如下:

[修饰符] 返回值类型 方法名(参数类型 参数名1, 参数类型 参数名2 ...) {
    ...
    方法体;
    ...
    return 返回值; // 可选,与返回值类型一致
}

比如常见的main方法如下:

public static void main(String []args) {
	System.out.println("Hello World!");
}

方法有如下几个部分组成:

  1. 修饰符:修饰符,这是可选的,定义了该方法的访问类型。比如public, static, private, protected等
  2. 返回值类型 :方法可能会返回值,支持前面介绍的八种基本数据类型以及String,如果不需要返回值,返回值类型就写成void。
  3. 方法名:是方法的实际名称,建议首字母小写。方法名和参数表共同构成方法签名。
  4. 参数类型:即形参列表,形参的个数可以是:0~N个。当方法被调用时,传递值给对应参数,这个值被称为实参。
  5. 方法体:方法体包含具体的语句,定义该方法的功能。
    下面是实现判断一个正整数是否是质数的函数的例子(假设num大于2):
private static boolean isPrimeNumber(int num) {
	boolean isPrime = true;
	for (int i = 2; i < num; i++) {
		if (num % i == 0) {
			isPrime = false;
			break;
		}
	}
	return isPrime;
}

方法内存

方法代码片段属于.class字节码文件的一部分,在调用方法的时候才会在中分配内存,称为压栈;方法执行结束释放方法的内存空间称为弹栈。方法执行完之后,方法内局部变量的空间也释放,因此局部变量只在方法内有效。JVM的栈中主要存储的是局部变量。

方法重载

方法重载(overload)主要是是指方法名相同,参数列表不同,和返回值类型无关,和修饰符无关。要构成方法重载需要满足以下条件:

  1. 方法是在同一个类当中
  2. 这些方法的方法名相同
  3. 参数列表不同,可以是数量不同,顺序不同,类型不同

面向对象

面向对象是Java核心的特点,主要有以下特性:

  • 封装:封装就是隐藏实现细节,仅对外提供访问接口。优点是使代码模块化,具有安全性。
  • 继承:继承就是将已存在的类(父类)的定义作为基础建立新类,新类(子类)的定义可以增加新的数据或新的功能,也可以用父类的功能
  • 多态:多态就是引用变量指向的具体类型和通过该引用变量发出的方法调用在编程时并不确定,而是在程序运行期间才确定。使得程序灵活地运行在多个状态。

对象和类的定义:

  • 对象(object):对象是类的一个实例,是实际存在的个体,有状态和行为。
  • 类(class):类是一个模板,它描述一类对象的行为和状态,是抽象思考的结果。

对象和类的关系:
一个类进行实例化就形成了对象,对象抽象形成类。

类的语法如下:

[修饰符列表] class 类名 {
	属性; // 对象的状态信息,通常采用变量方式定义,称为成员变量
	方法; // 对象的动作信息
}

类实例化需要用new运算符,语法如下:

new 类名();

java中的类属于引用数据类型,new新建的java对象存储在JVM的堆内存中,new等号左侧类的变量名存储的是指向堆内存的地址。每个new出来的类的内存互相独立。
Java面向对象中相关的重要知识点有:

  • 构造方法:构造方法名称与类名相同,无返回参数。构造方法在类初始化的时候调用,支持重载。类存在默认的无参构造方法。
  • this关键字:this指向当前对象的引用,"this.属性名称"或者"this.方法名称"用于访问本类的变量或者方法,在构造方法中使用"this();"语句访问本类的构造方法。
  • static关键字:static修饰属性表示静态变量,修饰类的方法表明无需类的对象就可以调用此方法。
  • super关键字:super为对父类的引用,可以使用super来调用父类的属性,方法,和构造方法。
  • final关键字:final修饰变量表示变量的值初始化后不能发生变化;final修饰方法表示不能被子类重写;final修饰的类无法被继承。
  • 抽象类:抽象类使用abstract关键字声明,非抽象类继承抽象类必须实现所有抽象方法,抽象类不能被实例化。抽象类不能声明为final。
  • instanceof关键字:instanceof 是用于检查对象是否为指定的类型,通常在进行类型转换时要使用,以避免发生类型转换异常。
  • 接口(Interface):接口是一个抽象类型,是抽象方法的集合。接口不是类,接口没有构造方法,不能被实例化,只能被类实现。接口只能包含 static 和 final 变量。

Java中声明一个接口的语法如下:

interface 接口名称 [extends 其他的接口名] {
  全局常量;
  抽象方法;
}

常用函数

接着介绍Java中使用非常频繁的几个函数:

输出函数

控制台的输出由 print() 和 println() 完成。这些方法都由类 PrintStream 定义,System.out 是该类对象的一个引用。print()打印指定的字符不换行,println()打印完成换一行。
下面是使用的例子:

System.out.print("Remember: ");
System.out.println("Haste makes waste");

输入函数

Java中使用java.util.Scanner类获取用户的输入,使用前需要先创建Scanner对象。常用next() 与 nextLine() 方法获取输入的字符串,对应地用hasNext() 与 hasNextLine() 判断是否还有输入的数据。
下面是使用next函数获取用户输入字符串的例子:

// 创建scanner对象
Scanner scan = new Scanner(System.in);

// 判断是否还有输入
if (scan.hasNext()) {
	String inputStr = scan.next();
	System.out.println("you input:" + inputStr);
}
// 关闭scanner
scan.close();

还可以使用nextInt接收一个整数,Scanner常用的方法如下表:

序号 方法 描述 判断是否有数据方法
01 next() 获取输入的字符串,不带空格 hasNext()
02 nextLine() 获取输入的一行字符串,支持空格,以Enter键结束 hasNextLine()
03 nextInt() 获取用户输入的整数 hasNextInt()
04 nextFloat() 获取用户输入的浮点数 hasNextFloat()

总结

Java这门语言涵盖的知识点比较丰富,一篇文章是不可能将所有知识点都完全覆盖到的。本文的主要目的是梳理下基础常见的知识点,帮助大家一起复习下,学习一门语言打好基础是至关重要的。掌握了这些基础知识点,自己动手写一些小程序问题也不大。文章最后再附上一个完整代码的小例子,实现的功能是将用户输入的字符串逆序输出:

class Test{  
    public static void main(String args[]) {
			Scanner scan = new Scanner(System.in);
		
			String inputStr = scan.nextLine();
		    // String转换为char数组
			char[] nums = inputStr.toCharArray();
		
			for (int i = nums.length; i>0; i--) {
				System.out.print(nums[i-1]);
			}
			System.out.println("");	
    }
}

你可能感兴趣的:(java,java)