java核心知识体系之基础总结篇二

java的基本数据类型

基本类型 位数 字节 默认值 取值范围
byte 8 1 0 -128 ~ 127
short 16 2 0 -32768 ~ 32767
int 32 4 0 -2147483648 ~ 2147483647
long 64 8 0L -9223372036854775808 ~ 9223372036854775807
char 16 2 ‘u0000’ 0 ~ 65535
boolean 1 false false、true
float 32 4 0f 1.4E-45 ~ 3.4028235E38
double 64 8 0d 4.9E-324 ~ 1.7976931348623157E308

byte数据类型

byte数据类型是8位的,有符号,以二进制补码表示的整数。
最小值:-128(-2^7)
最大值:127(2^7-1)
默认值: 0
byte类型的应用在大型数组中节约空间,主要替代整数,因为byte变量占用的空间只有int类型的四分之一。

byte a = 100; byte b = -50;

short数据类型

short数据类型是16位,有符号的以二进制补码表示整数。
最小值: -32768(-2^15)
最大值: 32767(-2^15-1)
short可以像byte那样节约空间,一个short类型的数据占的内存空间是int类型的二分之一。
默认值: 0

short a = 1000; short r = -200000;

int数据类型

int 数据类型是32位、有符号的以二进制补码表示的整数;
最小值: -2,147,483,648(-2^31);
最大值: 2,147,483,647(2^31 - 1);
一般地整型变量默认为 int 类型;
默认值是 0 ;

int a = 1; int b = -100;

long 数据类型

long 数据类型是 64 位、有符号的以二进制补码表示的整数;
最小值: -9,223,372,036,854,775,808(-2^63);
最大值: 9,223,372,036,854,775,807(2^63 -1);
这种类型主要使用在需要比较大整数的系统上;
默认值是 0L;

 long a = 100000LLong b = -200000L

float 数据类型

float 数据类型是单精度、32位、符合IEEE 754标准的浮点数;
float 在储存大型浮点数组的时候可节省内存空间;
默认值: 0.0f;
浮点数不能用来表示精确的值,如货币;

float f1 = 234.5f

double数据类型

double 数据类型是双精度、64 位、符合IEEE 754标准的浮点数;
浮点数的默认类型为double类型;
double类型同样不能表示精确的值,如货币;
默认值是 0.0d;

double d1 = 123.4

char 数据类型

char类型是一个单一的 16 位 Unicode 字符;
最小值: \u0000(即为 0);
最大值: \uffff(即为 65535);
char 数据类型可以储存任何字符;

char letter = 'A';(单引号)

boolean 数据类型

boolean数据类型表示一位的信息;
只有两个取值:true 和 false;
这种类型只作为一种标志来记录 true/false 情况;
默认值是 false;

boolean one = true

注意: 在java中使用long数据类型的一定要在数值的后面添加上L,否则程序会将该变量当作整形变量解析。"L"理论上不分大小写,但是若写成"l"容易与数字"1"混淆,不容易分辩,所以最好大写。这八种基本类型都有对应的包装类分别为:Byte、Short、Integer、Long、Float、Double、Character、Boolean。

自动装箱和拆箱

自动装箱与拆箱: Java 编译器在基本数据类型和对应的包装类之间做的一个转化。例如如:把 int 转化成 Integer, double转化成 Double 等等。反之就是自动拆箱。
原始类型: boolean、 char、 byte、 short、 int、 long、 float、 double
封装类型: Boolean、 Character、 Byte、 Short、 Integer、 Long、 Float、 Double
实例代码:

public class Demo {
    
    

    public static void main(String[] args){
    
    
       Integer a = 100;
       int b = a;
    }
}

字节码文件:

 0 bipush 100
 2 invokestatic #2 <java/lang/Integer.valueOf : (I)Ljava/lang/Integer;>
 5 astore_1
 6 aload_1
 7 invokevirtual #3 <java/lang/Integer.intValue : ()I>
10 istore_2
11 return

代码分析:
从字节码文件中可以得出当程序需要装箱时,就会调用对应的包装类的valueof 方法,而拆箱就是调用对应的xxxValue方法。由此可以得出上面的两行代码可以等价于下面的代码。

Integer a = 100 等价于:Integer a = Integer.valueOf(100);
int b = a 等价于: int b = a.intValue();

java的标识符和关键字

在程序中,我们需要不断地创建名字用以命名类和变量等,这些就叫标识符,但是在程序中有一些标识符已经被内部赋予了特殊的含义了,这些包含有特殊的含义的标识符就是关键字。比如生活中人们开一家店,可以命名为杂货店或是其他名字,但是就是不可以命名为警察局或者是派出所等等。

java的关键字

访问控制关键字

在这里插入图片描述

private关键字: private修饰的方法或者是属性只允许当前类访问,不允许其他任何的访问途径,子类是可以继承并访问父类的所有非private的方法和属性。

public关键字: public关键字可以修饰类,一旦使用public修饰类,则该类的源文件要与类名相同,否则编译不通过。一个类是作为外部类的时候,只能被public修饰或者不写修饰符。如果类作为内部类,那么可以使用四种修饰符修饰,因为此时的类是作为外部类的属性而存在的。public修饰的属性和方法可以被任何类访问,通过创建该类的对象可以对public修饰的方法和属性进行操作。另外,使用public修饰的属性和方法也可以通过子类继承下来。对方法而言,如果子类重写了父类的方法,子类对象访问该方法的时候优先访问子类的重写的方法,但是属性相反,子类对象优先访问父类的属性。

protected关键字: protected定义的是受保护的,受到该类所在的包的保护。被protected修饰的属性和方法可以被该包下的所有类访问到,同时也可以被该类的所有子类继承下来,也就是说子类的实例可以访问父类的所有使用protected修饰的属性和方法。(子类的范围指的是同一个包下的所有的子类或者是不同包下的所有子类)

“friendly”: 定义为友好的,也就是不写任何的修饰符。对于该属性或方法,在同一个包中的所有类都可以访问,同时默认的权限修饰的属性和方法也可以被同一个包下的子类继承,也就是说只有同一个包下的子类才可以访问到父类的默认属性和方法。

其他关键字

图来源
abstract	class	extends	final	implements	interface	native

java的运算符

算术运算符

Java 支持所有的基本算术运算符 ,这些算术运算符用于执行基本的数学运算 ,常见的运算符有:加、减、乘、 除和求余等。

加法:

double a = 5 . 2 ;
double b = 3 . 1;
double sum = a + b ;
// sum 的值为 8 . 3
System.out.println(sum);
// + 还可以作为字符串的连接运算符 。

减法:

double a = 5 . 2 ;
double b = 3 .1;
doub1e sub = a - b ;
// sub 的值为 2 . 1
System.out.println(sub);

乘法:

double a = 5 . 2 ;
double b = 3 . 1 ;
double multiply = a * b ;
// multiply 的值为 16.12
System.out.println(mu1tiply);

除法: 对于除法,首先除数不可以是0,否则编译运行会出现问题,其次,当两个操作数都是整数类型的时候,得到的商也是整数,不满1的自动去除。比如说19/4得到的是4而不是5。如果两个操作数或者一个操作数是浮点数,那得到的结果也是浮点数。

public class DivTest{
    
    
	public static void main(String[] args){
    
    
		double a = 5.2;
		double b = 3.1;
		double div = a / b;
		// div的值将是1.6774193548387097
		System.out.println(div);
		// 输出正无穷大:Infinity
		System.out.println("5除以0.0的结果是:" + 5 / 0.0);
		// 输出负无穷大:-Infinity
		System.out.println("-5除以0.0的结果是:" + - 5 / 0.0);
		// 下面代码将出现异常
		// java.lang.ArithmeticException: / by zero
		System.out.println("-5除以0的结果是::" + -5 / 0);
	}
}

求余: 求余运算符的用法跟除法的类似,它的计算结果是使用第一个操作数除以第二个操作数 , 得到一个整除的结果后剩下的值就是余数。

public class ModTest{
    
    
	public static void main(String[] args){
    
    
		double a = 5.2;
		double b = 3.1;
		double mod = a % b;
		System.out.println(mod); // mod的值为2.1
		System.out.println("5对0.0求余的结果是:" + 5 % 0.0); // 输出非数:NaN
		System.out.println("-5.0对0求余的结果是:" + -5.0 % 0); // 输出非数:NaN
		System.out.println("0对5.0求余的结果是:" + 0 % 5.0); // 输出0.0
		System.out.println("0对0.0求余的结果是:" + 0 % 0.0); // 输出非数:NaN
		// 下面代码将出现异常:java.lang.ArithmeticException: / by zero
		System.out.println("-5对0求余的结果是:" + -5 % 0);
	}
}

自增和自减运算符: 自增(++)和自减(–)运算符有两个特点,其一,这运算符是单目运算符,只能操作一个操作数,其二,运算符只能操作单个数值类型(整形、浮点型)的变量,不可以操作常量或者是表达式。同时两种运算符可以出现在变量的左边或者是右边。如果运算符在变量的左边,那左边先执行操作(自加或者自减),然后才把变量放入到表达式中运算,如果运算符在变量的右边,先把变量放入到表达式中运算,然后再执行操作(自加或者自减)。例如下面的代码:

int a = 5 ;
//让 a 先执行算术运算,然后自加
int b = a++ + 6;
//输出 a 的值为 6 , b 的值为 11
System . out.print1n(a + " \ n " + b);

int a = 5 ;
//让 a 先自加,然后执行算术运算
int b = ++a + 6;
//输出 a 的值为 6 , b 的值为 12
System.out .print1n(a + " \ n " + b);

比较运算符

1、>:大于,只支持左右两边操作数是数值类型。如果前面变量的值大于后面变量 的值,则返回 true 。

2、>= :大于等于 , 只支持左右两边操作数是数值类型。如果前面变量的值大于等于后面变量的值,则返回 true。

3、<: 小 于,只支持左右两边操作数是数值类型。如果前面变量的值小于后面变量的值, 则返回 true 。

4、<=:小于等于,只支持左右两边操作数是数值类型。如果前面变量的值小于等于后面变量 的值,则返回 true 。

5、 ==: 等,如果进行比较的两个操作数都是数值类型,即使它们的数据类型不相同 ,只要它们的值相等,也都将返回 true 。 例如 97 == 'a’返回true。 5.0 == 5 也返回 true。 如果两个操作数都是引用类型,那么只有当两个引用变量的类型具有父子关系时才可以比较,而且这两个引用必须指向同一个对象才会返回true。Java 也支持两个 boolean 类型的值进 比较,例如. true = false将返回 false。

6、!=:不等于,如果进行 比较的两个操作数都是数值类型,无论它们的数据类型是否相同 , 只要它们的值不相等,也都将返回 true 。 如果两个操作数都是引用类型,只有当两个引用变量的类型具有父子关系时才可以比较,只要两个引用指向的不是同 一个对象就会返回 true 。

逻辑运算符

逻辑运算符用于操作两个boolean类型的变量或者是常量,常见的逻辑运算符有:

&&: 与,前后两个操作数必须都是 true 才返回 true , 否则返回 false 。
&:不短路与,作用与 &&相同,但不会短路 。
|| : 或,只要两个操作数中有一个是 true,就可以返回 true,否则返回 false
|: 不短路或,作用与 || 相同,但不会短路 。
!: 非,只需要 一个操作数,如果操作数为 true ,则返回 false ; 如果操作数为 false ,则返回 true ^ : 异或,当两个操作数不同时才返回 true ,如果两个操作数相同则返回 false 。

实例代码:

public class LogicOperatorTest{
    
    
	public static void main(String[] args){
    
    
		// 直接对false求非运算,将返回true
		System.out.println(!false);
		// 5>3返回true,'6'转换为整数54,'6'>10返回true,求与后返回true
		System.out.println(5 > 3 && '6' > 10);
		// 4>=5返回false,'c'>'a'返回true。求或后返回true
		System.out.println(4 >= 5 || 'c' > 'a');
		// 4>=5返回false,'c'>'a'返回true。两个不同的操作数求异或返回true
		System.out.println(4 >= 5 ^ 'c' > 'a');

		// 定义变量a,b,并为两个变量赋值
		int a = 5;
		int b = 10;
		// 对a > 4和b++ > 10求或运算
		if (a > 4 | b++ > 10){
    
    
			// 输出a的值是5,b的值是11。
			System.out.println("a的值是:" + a + ",b的值是:" + b);
		}

		// 定义变量c,d,并为两个变量赋值
		int c = 5;
		int d = 10;
		// c > 4 || d++ > 10求或运算
		if (c > 4 || d++ > 10){
    
    
			// 输出c的值是5,d的值是10。
			System.out.println("c的值是:" + c + ",d的值是:" + d);
		}
	}

位运算符

位运算的种类:

& :按位与 。当 两位同时为 1 时才返回 1 。
| : 按位或 。只要有一位为 1 即可返回 1 。
~ :按位非。单目运算符,将操作数的每个位(包括符号位 )全部取反 。
^ :按位异或 。 当两位相同时返回 0 , 不同时返回 1 。
<<:左移运算符 ,>> :右移运算符 ,>>> : 无符号右移运算符 。

一般的位运算法则:
在这里插入图片描述
基本数据类型的位运算法则:

1、对于低于int类型的(比如说byte类型、short类型、和char类型)操作数,运算是总是先转换为int类型后再移位。

2、对于int类型的整数移位,a>>b,当b>32时,系统首先使用b对32求余,(因为int类型的最大值只有32位)得到的结果才是真正的移位的位数。例如, a>>33 和a>>1 的结果完全一样,而 a>>32 的结果和 a 相同 。

3、对于 long 类型的整数移位 a>>b ,当 b>64 时,总是先用 b 对 64 求余(因为 long 类型是 64 位) ,得到的结果才是真正移位的位数 。

运算符的优先级

在这里插入图片描述

java语言的方法

方法的参数按值传递: 在方法中参数变量的使用方法和局部变量相同,唯一不同的是参数变量的初始值是由调用方提供的。方法处理的是参数的值,而非参数本身。
方法名可以被重载: Java的Math包使用这种方法为所有的原始数值类型实现了Math.abs()、Math.min()和 Math.max()函数。
方法只能返回一个值,但可以包含多个返回语句: 一个Java方法只能返回一个值,它的类型是方法签名中声明的类型。静态方法第一次执行到一条返回语句时控制权将会回到调用代码中。尽管可能存在多条返回语句,任何静态方法每次都只会返回一个值,即被执行的第一条返回语句的参数。
方法可以产生副作用: 方法的返回值可以是void,这表示该方法没有返值。

静态方法和非静态方法

首先静态方法不可以调用非静态成员,静态方法是属于一个类的内容,在类加载的时候就会被分配内存,而非静态成员属于实例对象,只有在类实例化之后才会存在,然后通过实例对象调用。由此就可以看出静态成员和非静态成员的区别,在类没有实例化的时候,静态方法就已经存在了,这个时候可以通过类名加方法名调用,但是此时内存中还不存在非静态成员,这个时候调用非静态成员属于非法操作。

两者的区别

1、调用方式不同
调用静态方法可以不需要等到类的实例化,可以直接通过类名.方法名这种方法调用,但是调用非静态方法必须要等到类的实例化之后,通过对象.方法名这种方法调用。但是不推荐使用对象.静态方法这种方法调用静态方法,这样子容易造成混扰,因为静态方法不属于这个类的对象,而是属于这个类的。

2、访问权限不同
静态方法在访问这个类的成员的时候只能访问这个类的静态成员(静态方法或者静态变量)而不能访问其他非静态成员(实例成员变量或者成员方法),但是实例方法不存在这个限制。

方法重载和方法重写

重载: 编译时多态、同一个类中同名的方法具有不同的参数列表、不能根据返回类型进行区分(函数调用时不能指定类型信息,编译器不知道要调用的是哪个函数);

重写(覆盖): 运行时多态,子类与父类之间、子类重写父类的方法具有相同的返回类型、更好的访问权限。

JDK和JRE和JVM的区别

JDK

JDK(Java SE Development Kit),java标准的开发包,提供了编译,运行java程序所需要的各种工具和资源,包括了java编译器,java的运行环境,以及常用的java的类库

JRE

JRE(Java Runntime Environment),java运行时环境,用于解析执行java的字节码文件,普通的用户只需要安装JRE来运行java程序即可,但是作为一名java的开发者,必须要安装JDK来编译和调试程序。

JVM

在这里插入图片描述
JVM(Java Virtual Menchinal),JVM是运行java字节码文件的虚拟机,同时也是JRE的一部分,它是整个java实现跨平台开发的关键,负责解析执行字节码文件。所有平台上的java虚拟机都向编译器提供相同的接口,因此编译器只需要面向虚拟机,生成虚拟机可以字节码代码文件,由虚拟机执行即可。

什么是跨平台性?

跨平台性: 使用java语言编写的程序,可以实现一次编译在多个平台系统上运行。
实现原理: Java程序是通过java虚拟机在平台系统上运行的,只要该系统可以安装相对应的java虚拟机,那么这个系统就可以运行java程序。

为什么要采用字节码?

在java的运行过程中,JVM 可以理解的代码文件为字节码(即java程序经过java虚拟机编译器编译后扩展名为.class的文件),它不面向任何的特定的处理器,java通过字节码的方式在一定程序上解决了运行效率低下的问题,同时又保留了解析型语言可移植性的特点。因此java程序运行比较高效而且可以在不同的平台上运行。

Object类的公有方法解析

Object类的常见API方法详解:

protected Object clone():创建并返回此对象的副本。
boolean equals​(Object obj):指示某个其他对象是否“等于”此对象。
protected void finalize():已过时(Java11官方API文档)。
类<?> getClass():返回此 Object的运行时类。
int hashCode():返回对象的哈希码值。
void notify():唤醒正在此对象监视器上等待的单个线程。
void notifyAll():唤醒等待此对象监视器的所有线程。
String toString():返回对象的字符串表示形式。
void wait():导致当前线程等待它被唤醒,通常是 通知或中断 。
void wait​(long timeoutMillis):导致当前线程等待它被唤醒,通常是通知或中断,或者直到经过一定量的实时。
void wait​(long timeoutMillis, int nanos):导致当前线程等待它被唤醒,通常是通知或中断 ,或者直到经过一定量的实时。

猜你喜欢

转载自blog.csdn.net/m0_46198325/article/details/123937163
今日推荐