12.15_学习Java的day02(详解)

进制

1、计算机世界中只有二进制。

那么在计算机中存储和运算的所有数据都要转为二进制。
包括数字、字符、图片、声音、视频等。

2、计算机中的存储单位

(1)最小单位是比特(bit),即一位二进制值,要么0要么是1
(2)最基本单位是字节(byte),(1字节 = 8位)(1byte = 8bit)
1024byte = 1KB
1024KB = 1MB
1024MB = 1GB
1024GB = 1TB
1024TB = 1PB

10月24日是程序员节。

很多硬件厂商的换算单位。1000byte=1KB。
网络带宽:100Mb 这个b是bit。
100Mb = 100/8MB

3、 八种基本数据类型

(1)byte:字节类型,占1个字节,占8位,-128~127
(2)short:短整型,占2个字节,占16位,-32768~32767
(3)int:整型,占4个字节,占32位,-2的31次方~2的31次方-1
(4)long:长整型,占8给字节,占64位,-2的63次方~2的63次方-1
(5)float:单精度浮点型,占4个字节,占32位
(6)double:双精度浮点型,占8个字节,占64位
(7)char:字符型,占2个字节,而且无符号,0~65535
(8)boolean:布尔型,在实际中用1表示true,0表示false。只需要1位就够了。

4、如何存储?

规定
(1)为了数据的存储和运算的简便处理,计算机世界中发明了原码、反码、补码的概念。
本质上,计算机世界中只有补码。原码、反码是认为为了换算和理解补码提出的概念。
(2)最高位是符号位
1表示负数
0表示正数
(3)正数三码合一:原码、反码、补码都一样
负数三码不同:
负数的原码:最高位是1,其余位数它的绝对值的二进制值
负数的反码:最高位不变,其余位数在原码基础上取反(0变1,1变0)
负数的补码:在反码的基础上 加 1

例如:
正数:25 二进制:11001
如果25是byte类型,完整的二进制 00011001
如果25是int类型,完整的二进制 0000 0000 0000 0000 0000 0000 0001 1001
负数:-25
以byte为例
负数的原码:10011001
负数的反码:11100110
负数的补码:11100111

5、为什么byte类型是-128~127?

byte类型是8位。
正数的范围:
0000 0001: 1
0111 1111:127

中间的0:
0000 0000 :0 用它表示0
1000 0000 : 0 不用它表示0,用它来表示别的

负数的范围:
1000 0001:-127
补码:1000 0001
反码:1000 0000
原码:1111 1111
1111 1111:-1
补码:1111 1111
反码:1111 1110
原码:1000 0001

-127 -1 = -127 + (-1)= 1000 0001 + 1111 1111 = 1 1000 0000 = -128
但是byte只能表示8位,最左边的截掉,剩下的是 1000 0000 ,就用它来表示-128。

6、float和double如何存储?

(1)小数如何变为二进制?(了解)
整数部分:除2倒取余
小数部分:乘2取整数部分

小数的存储分为三个部分:
①符号位
②指数位:float有8位指数位 255次 结论1:因为指数的增长非常快,float的4个字节比long类型的8个字节数据范围大。
double有11位指数位 n次
③尾数:float有23位
double有52位 结论2:double比float的精度范围大

	有的小数在转为二进制时,会出现*2一直循环或者超过float和double的尾数范围。
									结论3:float和double是浮点类型,不是定点类型,即不精确。

7、char类型是如何存储的?

Java中char类型的字符,使用Unicode字符集,将所有的字符进行编码。
每一个字符都一个唯一的Unicode编码值。
例如:
a:97 b:98
A:65 B:66
0:48 1:49

计算机早期只能表示128个字符,ASCII码表。
Unicode字符集兼容ASCII码表。

数据类型的转换

(1)基本数据类型的转换
(2)引用数据类型的转换(今天不讨论它)

一、基本数据类型的转换

1、自动类型转换

(1)当我们把存储范围小的类型的值/变量/表达式的结果赋值给存储范围大的类型的变量
例如:int num = ‘男’; 把char类型值赋值给int类型的变量num
(2)当byte与byte,short与short,char与char,或者它们三个之间的运算,都会自动升级为int
(3)当很多种基本数据类型的值一起混合运算时,结果是升级为它们当中最大的类型。
(4)boolean不参与数据类型转换

2、强制类型转换

格式:
(强制为xx类型)变量或值或(表达式)
(1)当我们把存储范围大的类型的值/变量/表达式的结果赋值给存储范围小的类型的变量
例如:int num = 97;
char c = (char)num;
注意:这种情况的强制是有风险:可能溢出或损失精度
(2)当我们需要强制“提升”某个变量或值的数据类型时,也可以使用强制类型转换
这种情况不会溢出后损失精度,只是类型转换
(3)boolean不参与数据类型转换

3、特殊的类型String

凡是与字符串进行“+”拼接运算,结果就是字符串。

class Test{
	public static void main(String[] args){
		//左边num是int,右边的'男'是char类型
		//自动类型转换
		int num = '男';
		System.out.println(num);//30007
		
		//强制类型转换
		char gender = (char)num;
		System.out.println(gender);//男
		
		//自动类型转换
		long bigNum = 1234567L;
		float f = bigNum;
		System.out.println(f);//1234567.0
		
		byte b1 = 1;
		byte b2 = 2;
		//byte b3 = b1 + b2;
		byte b3 = (byte)(b1 + b2);
		System.out.println("b3 = " + b3);
		
		short s1 = 1;
		short s2 = 2;
		//short s3 = s1 + s2;
		
		char c1 = '0';
		char c2 = '1';
		//char c3 = c1 + c2;
		
		//char c3 = b1 + s1;
		
		double d = 1.0;
		double sum = b1 + s1 + c1 + bigNum + f + d;
		
		int a = 1;
		int b = 2;
		//double result = 1/2;//0.0
		double result = (double)a/b;//0.5  把a强制为double类型
		System.out.println("result = " + result);
		
		int i = 130;
		byte j = (byte)i;//-126
		System.out.println("j = " + j);
		
		double price = 34.67;
		int p = (int)price;
		System.out.println("p = " + p);
		
		//字符串的拼接
		String str = "hello" + 1;
		System.out.println("str = " +  str);
		
		System.out.println('a' + 'b' + "=");//195=
		System.out.println("=" + 'a' + 'b' );//=ab
		System.out.println('a' + "=" + 'b' );//a=b
	}
}

进制的表示

十进制:正常表示
二进制:在数字前面加0B或0b
八进制:在数字前面加0
十六进制:在数字前面加0X或0x

运算符

一、算术运算符

加:+
(1)如果是基本数据类型相加 表示求和
(2)如果是与字符串进行相加 表示拼接
减:-
乘:*
除:/
如果两个整数相除,结果只保留整数部分
模(取余):%
余数的正负号,只看被除数,被模数

被除数 / 除数 = 商  .... 余数
被除数 = 商 * 除数 + 余数
被除数(-5) / 除数(-2) = 商(2)....余数(-1)
被除数(-5) = 除数(-2) * 商(2) + 余数(-1) = -4 - 1= -5

正号:+
负号:-

自增:++
某个变量的值自增1
自减:–
某个变量的值自减1

如果自增自减变量单独运算,++/–在前还是在后,都一样;
如果自增自减变量与其他变量一起运算,++/–在前,先自增/自减然后再取自增变量的值去参与其他运算;
++/–在前,先取自增变量的值放到操作数栈中,然后紧接着做自增/自减,然后再运算其他的;

Arithmetic:算术

class Arithmetic{
	public static void main(String[] args){
		System.out.println(1 + 2);
		System.out.println(1 - 2);
		System.out.println(1 * 2);
		System.out.println(1 / 2);
		System.out.println(1 % 2);
		
		System.out.println("---------------------------");
		System.out.println(5 / 2);//2
		System.out.println(-5 / -2);//2
		System.out.println(-5 / 2);//-2
		System.out.println(5 / -2);//-2
		
		System.out.println("---------------------------");
		System.out.println(1 % 2);//1
		System.out.println(-1 % -2);//-1
		System.out.println(-1 % 2);//-1
		System.out.println(1 % -2);//1
		System.out.println("---------------------------");
		
		int a = 5;
		int b = -a;
		int c = +b;
		System.out.println("a = " + a);
		System.out.println("b = " + b);
		System.out.println("c = " + c);
		System.out.println("---------------------------");
		
		int i = 0;
		i++;  //自增1 i=1
		++i;  //自增1 i=2
		System.out.println("i = " + i);
		
		System.out.println("---------------------------");
		i = 0;
		int j = ++i;//(1)i先自增变为1(2)然后取出i的值,放到“操作数栈”的位置(3)赋值给j
		System.out.println("i = " + i);
		System.out.println("j = " + j);
		
		System.out.println("---------------------------");
		i = 0;
		int k = i++;//(1)先取出i的值0,放到“操作数栈”的位置(2)然后i自增(3)赋值给j
		System.out.println("i = " + i);
		System.out.println("k = " + k);
		
		System.out.println("---------------------------");
		int m = 0;
		m = ++m;//(1)先m自增(2)再取m的值1,放到“操作数栈”的位置(3)在把“操作数栈”的值赋值给m
		System.out.println("m = " + m);//m=1
		
		System.out.println("---------------------------");
		int n = 0;
		n = n++;//(1)先取n的值0,放到“操作数栈”的位置(2)n自增n=1(3)在把“操作数栈”的值0赋值给n
		System.out.println("n = " + n);//n=0
		
		System.out.println("---------------------------");
		int x = 1;
		int y = ++x * x++ + x++;
		/*
		(1)++x
			A:先x自增 x = 2
			B:取x的值2,放到“操作数栈”
		(2)x++
			A:先取x的值2,放到“操作数栈”
			B:x自增  x=3
		(3)取出“操作数栈”的两个值,2*2=4,重新放回“操作数栈”
		(4)x++
			A:先取x的值3,放到“操作数栈”
			B:x自增
		(5)取出“操作数栈”的两个值,4+3=7,重新放回“操作数栈”
		(6)取出“操作数栈”的结果,赋值给y
		*/
		System.out.println("x = " + x);
		System.out.println("y = " + y);
		
		System.out.println("---------------------------");
		int p = 1;
		int q = ++p + p++ * ++p;
		/*
		(1)++p
			A:先自增 p =2
			B:再取p的值2,放到“操作数栈”
		(2)p++ * ++p中先算
			①p++
				A:先取p的值2,放到“操作数栈”
				B:p自增 p=3
			②++p
				A:先自增 p =4
				B:再取p的值4,放到“操作数栈”
			③乘法  2*4=8
		(3)求和	2 + 8 = 10
		
		*/
		System.out.println("p = " + p);
		System.out.println("q = " + q);
	}
} 

二、赋值运算符

1、最基本的赋值运算符:=

运算的特点:
(1)永远是把=右边的xx赋值给=左边的变量
==> =左边一定是一个变量
(2)左边变量的类型,与右边的值的类型,要么一致或者兼容
一致:一样
兼容:可以同自动类型转换进行升级
(3)赋值一定是最后算的

2、扩展的赋值运算符

+=
-=
*=
/=
%=

中间不允许有空格

运算的特点:
(1)把 扩展的赋值运算符 左边的变量 与 右边的值/表达式再继续xx运算,结果赋值给左边的变量
(2)如果最后运算的结果的类型超过左边变量的类型,会发生自行发生强制类型转换
即要注意可能发生溢出或损失精度

Assign:委派,赋值

class AssignOperator{
	public static void main(String[] args){
		int x = 1;
		int y = 2;
		//x + y = 3;//错误的  左边x + y是一个表达式,不是变量
		int z = x + y; //左右两边的类型一样
		
		double d = 1; //左边是double,右边是int,int赋值给double是允许,可以自动类型转换
		
		int i = 1;
		i += 2; //等价于 i= i+2;
		System.out.println("i = " + i);//3
		
		int j = 3;
		j *= i + j;//等价于 j = j * (i+j);
		System.out.println("j = " + j);
		
		byte b1 = 127;
		byte b2 = 2;
		//b1 = b1 + b2;//右边是int,左边是byte
		b1 += b2;//等价于 b1 = (byte)(b1 + b2);
		System.out.println("b1 = " + b1);
	}
}

三、比较运算符

1、比较运算符的类型

大于:>
小于:<
大于等于:>=
小于等于:<=
等于:==
注意:与赋值运算符=的区别
不等于:!=

2、比较运算符的运行结果:true/false

3、比较运算符中的>,<,>=,<=

只支持:整型、浮点型、字符型,不支持boolean,也不支持String等引用数据类型。

对于比较运算符中的==和!=是支持所有类型的

class Compare{
	public static void main(String[] args){
		System.out.println(3 > 2);
		System.out.println(3 < 2);
		System.out.println(3 == 2);
		//System.out.println(3 = 2);//错误
		int a = 3;
		int b = 2;
		System.out.println(a = b);//把b中的值赋值给a,并显示a变量的值
		System.out.println("a = " + a);
		System.out.println("b = " + b);
		
		int age = 20;
		//判断这个age是否在[18,28]之间
		//System.out.println(18 <= age <= 28);//错误 18 <= age结果要么是true要么false,是boolean
		//System.out.println("hello" > "world");
		
		//System.out.println("hello" == "world");//可以,比较的是对象的地址
		
		int num = 10;
		double d = 10.0;
		System.out.println(num == d);//true  会发生自动类型转换
	}
}

四、逻辑运算符

1、逻辑运算符的类型:

逻辑与:&
只有左右两边都为true,结果才为true。
逻辑或:|
只要左右两边有一个为true,结果就为true。
逻辑非:!
取反,!true为false,!false为true
逻辑异或:^
只有当左右两边一个为true一个为false,结果才为true。
短路与:&&
只有左右两边都为true,结果才为true。
短路或:||
只要左右两边有一个为true,结果就为true。

2、特点

(1)逻辑运算符的左右两边必须是boolean类型
(2)逻辑运算符的运算结果还是boolean类型

3、逻辑与 和 短路与之间的区别

对于短路与&&,如果&&左边是false时,右边是不算的。
因为左边是false时,右边无论结果怎么样,最终都是false。
对于逻辑与&,不管左边是true还是false,右边都要计算。

同理

4、逻辑或 和 短路或之间的区别

对于短路或||,如果||左边是true时,右边就不算了。
对于逻辑或|,不管左边是true还是false,右边都要计算。

实际开发中,基本上使用短路&&和||,效率更高。

class LogicOperator{
	public static void main(String[] args){
		System.out.println(true & true);
		System.out.println(true & false);
		System.out.println(false & true);
		System.out.println(false & false);
		
		System.out.println("======================");
		System.out.println(true | true);
		System.out.println(true | false);
		System.out.println(false | true);
		System.out.println(false | false);
		
		System.out.println("======================");
		System.out.println(true ^ true);
		System.out.println(true ^ false);
		System.out.println(false ^ true);
		System.out.println(false ^ false);
		
		System.out.println("======================");
		System.out.println(true && true);
		System.out.println(true && false);
		System.out.println(false && true);
		System.out.println(false && false);
		
		System.out.println("======================");
		System.out.println(true || true);
		System.out.println(true || false);
		System.out.println(false || true);
		System.out.println(false || false);
		
		System.out.println("======================");
		System.out.println(!true);
		System.out.println(!false);
		
		System.out.println("======================");
		int i = 1;
		System.out.println(i<0 & ++i > 1);
		System.out.println("i = " + i);
		
		System.out.println("======================");
		int j = 1;
		System.out.println(j<0 && ++j > 1);
		System.out.println("j = " + j);
		
		System.out.println("======================");
		int age = 20;
		//判断这个age是否在[18,28]之间
		System.out.println(18 <= age  &&  age<=28);
	}
}

五、条件运算符

1、格式

条件表达式/布尔值 ? 结果表达式1/结果值1 : 结果表达式2/结果值2

2、运算规则

如果 “条件表达式/布尔值"的结果是true,那么整个表达式的结果就取 ”结果表达式1/结果值1"的值,否则就取“结果表达式2/结果值2”的值

运算符的分类:

按照功能分:算术运算符、赋值运算符、比较运算符、逻辑运算、条件运算符…
按照操作数个数分:一元运算符(单目运算符)、二元运算符(双目运算符)、三元运算符 (三目运算符)
一元运算符:操作数只有一个
例如:正号(+) +a
负号(-) -a
自增自减 ++i i++
逻辑非: !true

二元运算符:操作数有两个
例如:加法:a+b
减法:a-b
大于:a>b
逻辑与:a&b
三元运算符:条件 ? 结果1 : 结果2

class ConditionOperator{
	public static void main(String[] args){
		boolean marry = true;
		System.out.println(marry ? "已婚" : "未婚");
		
		marry = false;
		System.out.println(marry ? "已婚" : "未婚");
		
		//找两个整数中的最大值
		int a = 1;
		int b = 2;
		System.out.println("最大值是:" + (a>=b ? a : b));
		
		//找出三个数中的最大值
		int x = 1;
		int y = 2;
		int z = 0;
		
		//如果x>=y成立,把x的值赋值给max,否则把y的值赋值给max
		int max = x>=y ? x : y; 
		max = max >= z ? max : z;
		System.out.println("最大值是:" + max);
	}
}

六、位运算符

1、位运算符的类型

(1)左移:<<
左移几位,相当于乘以2的几次方
(2)右移:>>
右移几位,相当于除以2的几次方,如果不能整除往下取整
(3)无符号右移:>>>
对于正数来说,没区别
对于负数来说,无符号右移之后,左边是补0,所以会导致负数变为正数
(4)按位与:&
两个数对应的位,1&1为1,1&0为0,0&1为0,0&0为0(有0则0)
(5)按位或:|
两个数对应的位,1|1为1,1|0为1,0|1为1,0|0为0(有1则1)
(6)按位异或:^
两个数对应的位,1 ^ 1为0,1 ^ 0为1,0 ^ 1为1,0 ^ 0为0(相同为0,不同为1)
(7)按位取反
原来位是1变为0,0变为1

2、位运算符的特点

(1)要求操作数必须是整型
(2)位运算符是在值的补码形式上进行计算的
(3)阅读性不是很强,因为人不能一眼看到结果,
但是它的效率是非常高。

class Bit{
	public static void main(String[] args){
		double d = 1.2;
		//System.out.println(d >>2);//错误,操作数类型错
		
		System.out.println(1 << 4);//16
		/*
		1的补码:0000 0000 0000 0000 0000 0000 0000 0001
		1<<4:   0000 0000 0000 0000 0000 0000 0001 0000
		*/
		
		System.out.println(10 << 4);//160
		/*
		10的补码:0000 0000 0000 0000 0000 0000 0000 1010
		10<<4:   0000 0000 0000 0000 0000 0000 1010 0000
		*/
		
		System.out.println(125 >> 4);//7
		/*
		125的补码:0000 0000 0000 0000 0000 0000 0111 1101
		125>>4:   0000 0000 0000 0000 0000 0000 0000 0111
		*/
		
		System.out.println(-125 >> 4);//-8
		/*
		-125的原码:1000 0000 0000 0000 0000 0000 0111 1101
		-125的反码:1111 1111 1111 1111 1111 1111 1000 0010 
		-125的补码:1111 1111 1111 1111 1111 1111 1000 0011 
		-125>>4:   1111 1111 1111 1111 1111 1111 1111 1000(补码)
		-125>>4:   1111 1111 1111 1111 1111 1111 1111 0111(反码)
		-125>>4:   1000 0000 0000 0000 0000 0000 0000 1000(原码)
		*/
		
		System.out.println(125 >>> 4);//正数的右移和无符号右移是一样的
		System.out.println(-125 >>> 4);
		/*
		-125的原码:1000 0000 0000 0000 0000 0000 0111 1101
		-125的反码:1111 1111 1111 1111 1111 1111 1000 0010 
		-125的补码:1111 1111 1111 1111 1111 1111 1000 0011 
		-125>>>4:   0000 1111 1111 1111 1111 1111 1111 1000(补码)
		*/
		
		System.out.println(125 & 4);
		/*
		125的补码:0000 0000 0000 0000 0000 0000 0111 1101
		4的补码:  0000 0000 0000 0000 0000 0000 0000 0100
		125 & 4:  0000 0000 0000 0000 0000 0000 0000 0100
		*/
		
		System.out.println(125 & 10);//8
		/*
		125的补码: 0000 0000 0000 0000 0000 0000 0111 1101
		10的补码:  0000 0000 0000 0000 0000 0000 0000 1010
		125 & 10:  0000 0000 0000 0000 0000 0000 0000 1000
		*/
		
		System.out.println(125 | 10);//127
		/*
		125的补码: 0000 0000 0000 0000 0000 0000 0111 1101
		10的补码:  0000 0000 0000 0000 0000 0000 0000 1010
		125 | 10:  0000 0000 0000 0000 0000 0000 0111 1111
		*/
		
		System.out.println(125 ^ 10);//119
		/*
		125的补码: 0000 0000 0000 0000 0000 0000 0111 1101
		10的补码:  0000 0000 0000 0000 0000 0000 0000 1010
		125 ^ 10:  0000 0000 0000 0000 0000 0000 0111 0111
		*/
		
		System.out.println(~10);//-11
		/*
		10的补码:  0000 0000 0000 0000 0000 0000 0000 1010
		~10:		1111 1111 1111 1111 1111 1111 1111 0101(补码)
		~10:		1111 1111 1111 1111 1111 1111 1111 0100(反码)
		~10:		1000 0000 0000 0000 0000 0000 0000 1011(原码)
		*/
		
		System.out.println(1 << 33);
		/*
		1的补码:0000 0000 0000 0000 0000 0000 0000 0001
		1<<33:  0000 0000 0000 0000 0000 0000 0000 0010
		等价于1<<(33-32)
		*/
		
		System.out.println(4 >> 33);
		/*
		4的补码:0000 0000 0000 0000 0000 0000 0000 0100
		4>>33:  0000 0000 0000 0000 0000 0000 0000 0010
		等价于4>>(33-32)
		*/
		
		byte b = 1;
		System.out.println(b << 2);//4
		/*
		byte按理1个字节
		1的补码:0000 0001
		b<<2:   0000 0000 0000 0000 0000 0000 0000 0100
		*/
		System.out.println(b << 9);//512
		/*
		byte按理1个字节,byte类型运算升级为int
		1的补码:0000 0001
		b<<9:   0000 0000 0000 0000 0000 0010 0000 0000
		*/
	}
}

运算符的优先级:

(1)赋值类运算符是最低,也就最后算
(2)大体的排序:算术–>位–>比较–>逻辑–>三元–>赋值

如果我们记不清具体的运算符的优先级,建议:

(1)不要写太复杂的式子
(2)你想要先算的加()

在程序中如何表示一个字符?

(1)可见字符:‘一个字符’

(2)不可见字符:

换行:\n
回车:\r
制表位:\t
退格:\b
斜杠:\
双引号:"
单引号:’

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值