/*
运算符:
2、赋值运算符
(1)基本的赋值运算符:=
赋值操作:永远是把=右边的常量值、变量中值、表达式计算的值赋值给=左边的变量,
即=左边只能是一个变量。
运算的顺序:把右边的整个表达式先算完,才会做最后的赋值操作。
(2)扩展的赋值运算符
例如:
+=
-=
*=
/=
%=
...
*/
class Test09_Assign{
public static void main(String[] args){
int x = 1;
int y = 2 ;
int z = 3;
//x + y = z;//=左边只能是一个变量
byte b1 = 1;
byte b2 = 2;
//b2 = b1 + b2;//右边byte + byte结果是int
b2 += b1;//等价于 b2 = (byte)(b2 + b1);
System.out.println("b1 = " + b1);//1
System.out.println("b2 = " + b2);
System.out.println("---------------------------");
int i = 1;
int j = 5;
j *= i++ + j;
System.out.println("i = " + i);//2
System.out.println("j = " + j);//30
}
}
class Test09_Modify{
public static void main(String[] args){
int i = 1;
int j = 5;
//j *= i++ + j; 等加于 j = j * (i++ + j);
/*
第一步:先把j的值“5”放起来
第二步:i++
(1)先取i的值“1”,放起来
(2)i自增,i=2
第二步:求和
1 + 5 = 6
第三步:乘
j * (和) = 5 * 6 = 30
第四步:赋值,把乘积赋值给j
*/
j *= i++ + j;
System.out.println("i = " + i);//2
System.out.println("j = " + j);//30
}
}
class Test09_Modify2{
public static void main(String[] args){
int i = 1;
int j = 5;
//j *= i++ + j++; 等加于 j = j * (i++ + j++);
/*
第一步:先把j的值“5”放起来
第二步:i++
(1)先取i的值“1”,放起来
(2)i自增,i=2
第三步:j++
(1)先取j的值“5”
(2)在j自增 j = 6
第四步:求和
1 + 5 = 6
第三步:乘
用“5” * (和) = 5 * 6 = 30
第四步:赋值,把乘积赋值给j
*/
j *= i++ + j++;
System.out.println("i = " + i);//2
System.out.println("j = " + j);//30
}
}
/*
运算符:
3、比较运算符
大于:>
小于:<
大于等于:>=
小于等于:<=
等于:==
注意,谨防与赋值的=混淆
不等于:!=
比较运算符,计算完后的结果只有两个:true,false
说明比较运算符的表达式,可以作为(1)判断的条件(2)逻辑运算符的操作数
比较运算符能够用于基本数据类型,不能用于引用数据类型。
除了==和!=,关于引用数据类型时它俩的意义后面再讲。
一元运算符:操作数只有一个
例如:a++ 其中a就是操作数
-a 其中a就是操作
二元运算符:需要两个操作数
例如:求和 a+b 其中a和b就是操作
比较大小 age>=18 其中的age和18都是操作数
三元运算符:需要三个操作数
...
*/
class Test10_Compare{
public static void main(String[] args){
/*
有一个变量age,表示年龄,判断是否成年(满足18岁)
*/
int age = 26;
System.out.println("是否成年:" + (age>=18));
/*
比较运算符作为条件
*/
if(age >= 18){
System.out.println("祝你玩得愉快!");
}else{
System.out.println("未成年不得进入!");
}
/*
有一个变量,存储的是boolean类型的值
*/
boolean flag = false;
if(flag == true){//不会修改flag里面的值
System.out.println("条件成立");
}
//与上面的语句是等价的
if(flag){
System.out.println("条件成立");
}
if(flag = true){//不是比较,而是赋值,结果仍然是布尔值,只要是布尔值就可以作为条件
System.out.println("条件成立");
}
System.out.println("flag = " + flag);
/*
有一个变量,存储的是其他类型的值
*/
int num = 1;
if(num == 1){
System.out.println("num=1");
}
//if(num = 1){//错误的,因为num=1是赋值表达式,结果还是int,int值是不能作为条件的
// System.out.println("num=1");
//}
}
}
/*
运算符:
4、逻辑运算符
逻辑与:&
类似于:且
true & true 结果为true
true & false 结果为false
false & true 结果为false
false & false 结果为false
逻辑或:|
类似于:或
true | true 结果为true
true | false 结果为true
false | true 结果为true
false | false 结果为false
逻辑非:!
类似于:取反
!true 结果为false
!false 结果为true
逻辑异或:^
类似于:求不同
true ^ true 结果为false
true ^ false 结果为true
false ^ true 结果为true
false ^ false 结果为false
短路与:&&
结果:和&是一样的
运算规则:如果&&的左边已经是false,右边就不看了
true & true 结果为true
true & false 结果为false
false & ? 结果为false
false & ? 结果为false
短路或:||
结果:和|是一样的
运算规则:如果||左边已经是true,右边就不看了
true | ? 结果为true
true | ? 结果为true
false | true 结果为true
false | false 结果为false
*/
class Test11_Logic{
public static void main(String[] args){
/*
判断成绩是否在70和80之间
数学:70<=score<=80
Java中:
*/
int score = -78;
/*
Test11_Logic.java:14: 错误: 二元运算符 '<=' 的操作数类型错误
if( 70<=score<=80){
^
第一个类型: boolean 70<=score的运算结果是true或false
第二个类型: int
1 个错误
*/
//if( 70<=score<=80){
// System.out.println("良好");
//}
if(70<=score & score<=80){
System.out.println("良好");
}
/*
假设成绩合理范围[0,100]
判断成绩是否小于0 或 大于100,输出成绩有误
*/
if(score<0 | score>100){
System.out.println("成绩有误");
}
/*
假设成绩合理范围[0,100]
判断成绩是否在合理范围内
*/
if(score>=0 & score<=100){
}
//或下面这么写
if(!(score<0 | score>100)){
}
System.out.println(true ^ true);
System.out.println(true ^ false);
System.out.println(false ^ true);
System.out.println(false ^ false);
/*
短路与:&&
短路或:||
*/
int i = 1;
int j;
/*
第一步:i++
(1)先取i的值“1”,放起来
(2)在i自增,i=2
第二步:算比较
放起来的“1” == 1比较,成立
&&左边是true,不会短路
第三步:++i
(1)先自增i=3
(2)再取i的值“3”,放起来
第四步:比较
放起来的“3” == 2比较,结果是false,不成立
第五步:
左边的true && 右边的false运算,结果为false,总的if不成立,走else
*/
//if(i++ == 1 && ++i == 2){
// j = 1;
//}else{
// j = 2;
//}
/*
第一步:i++
(1)先取i的值“1”,放起来
(2)在i自增,i=2
第二步:算比较
放起来的“1” == 1比较,成立
||左边是true,会发生短路,右边不看了(++i == 2)没运算
第三步:
true || ?,结果为true,总的if成立
*/
if(i++ == 1 || ++i == 2){
j = 1;
}else{
j = 2;
}
System.out.println("i = " + i);
System.out.println("j = " + j);
}
}
class Test12_Exer1{
public static void main(String[] args){
int x = 1;
int y = 1;
/*
第一步:x++
(1)先取x的值“1”
(2)再x自增x = 2
第二步:比较
用“1”与2比较, 1==2,不成立,false
因为&不是短路与,不管左边是怎么样,右边继续
第三步:++y
(1)自增 y = 2
(2)取y的值“2”
第四步:比较
用“2”与2比较 2 == 2,成立,true
第五步:逻辑
false & true,结果为false,总的if不成立
*/
if(x++ == 2 & ++y==2){
x = 7;
}
System.out.println("x = " + x + ",y = " + y);//x = 2,y = 2
}
}
class Test12_Exer2{
public static void main(String[] args){
int x = 1;
int y = 1;
/*
第一步:x++
(1)先取x的值“1”
(2)再x自增x = 2
第二步:比较
用“1”与2比较, 1==2,不成立,false
因为&&是短路与,左边为false,右边就不看了
第三步:逻辑
false & ?,结果为false,总的if不成立
*/
if(x++ == 2 && ++y==2){
x = 7;
}
System.out.println("x = " + x + ",y = " + y);//x = 2,y = 1
}
}
class Test12_Exer3{
public static void main(String[] args){
int x = 1;
int y = 1;
/*
第一步:x++
(1)先取x的值“1”
(2)再x自增x = 2
第二步:比较
用“1”与1比较, 1==1,成立,true
中间是|,不是短路或,右边要继续
第三步:++y
(1)y先自增,y=2
(2)再去y的值“2”
第四步:比较
用“2”与1比较 2==1,不成立,结果为false
第五步:逻辑
true & false,结果为true,总的if成立,要执行x = 7
*/
if(x++ == 1 | ++y==1){
x = 7;
}
System.out.println("x = " + x + ",y = " + y);//x = 7,y = 2
}
}
class Test12_Exer4{
public static void main(String[] args){
int x = 1;
int y = 1;
/*
第一步:x++
(1)先取x的值“1”
(2)再x自增x = 2
第二步:比较
用“1”与1比较, 1==1,成立,true
中间是||,是短路或,左边已经为true,会发生短路现象,右边不看了
第五步:逻辑
true & ?,结果为true,总的if成立,要执行x = 7
*/
if(x++ == 1 || ++y==1){
x = 7;
}
System.out.println("x = " + x + ",y = " + y);//x = 7,y = 1
}
}
class Test13_Exer{
public static void main(String[] args){
boolean x = true;
boolean y = false;
short z = 42;
/*
第一步:z++
(1)先取z的值“42”
(2)z自增 z=43
第二步:比较
用“42”与42比较,条件成立,true
中间是&&,短路与,但是没有满足短路现象。右边继续
第三步:
取y的值false
第四步:
比较,用"false"与true比较,条件不成立,false
第五步:
true && false,结果为false,if条件不成立,z++不执行
*/
if((z++==42) && (y==true))
z++;
/*
||左边:x=false,这是赋值运算,结果仍然是false
中间||,是短路或,但是没有满足短路现象,右边继续
右边:
++z:先自增z=44,然后取z的值“44”,然后与45进行比较,结果为false
左边的false || 右边的false,结果还是false,if不成立,z++不执行
*/
if((x=false) || (++z==45))
z++;
System.out.println("z = " + z);//44
}
}
class Test13_Exer2{
public static void main(String[] args){
boolean x = true;
boolean y = false;
short z = 42;
/*
这里y=true是赋值,结果还是true,表示条件成立,并且y的值已经变为true
*/
if(y=true)
/*
第一步:z++
(1)先取z的值“42”
(2)z自增 z=43
第二步:比较
用“42”与42比较,条件成立,true
中间是&&,短路与,但是没有满足短路现象。右边继续
第三步:
取y的值true
第四步:
比较,用"true"与true比较,条件成立,true
第五步:
true && true,结果为true,if条件成立,z++执行
z = 44
*/
if((z++==42) && (y==true))
z++;
/*
||左边:x=false,这是赋值运算,结果仍然是false
中间||,是短路或,但是没有满足短路现象,右边继续
右边:
++z:先自增z=45,然后取z的值“45”,然后与45进行比较,结果为true
左边的false || 右边的true,结果还是true,if成立,z++执行,z=46
*/
if((x=false) || (++z==45))
z++;
System.out.println("z = " + z);//46
}
}
/*
运算符:
5、条件运算符,
因为它是唯一的三元运算符,所以也称为三元运算符
条件表达式 ? 结果表达式1 : 结果表达式2
整个表达式包含三个部分。
运算规则:如果条件表达式成立,就取结果表达式1的值,否则就取结果表达式2的值
*/
class Test14_Condition{
public static void main(String[] args){
boolean marry = false;
System.out.println(marry ? "已婚" : "未婚");
//找出x和y中的最大值
int x = 4;
int y = 4;
int max = x>=y ? x : y;
/*
等价于
if(x>=y){
max = x;
}else{
max = y;
}
*/
System.out.println(x + "," + y + "中的最大值是:" + max);
}
}
/*
运算符:(了解)
6、位运算符
效率很高,但是可读性不好
因为它是基于二进制补码直接运算的。
左移:<<
运算规则:<<几位,就乘以2的几次方
二进制补码左移n位,右边补0
右移:>>
运算规则:>>几位,就除以2的几次方
二进制补码右移n位,左边补0还是1,看最高位
无符号右移:>>>
运算规则:二进制补码右移n位,左边补0,对于负数来说,移完后,变为正数
按位与:&
1 & 1 结果1
1 & 0 结果0
0 & 1 结果0
0 & 0 结果0
按位或:|
1 | 1 结果1
1 | 0 结果1
0 | 1 结果1
0 | 0 结果0
按位异或:^
1 ^ 1 结果0
1 ^ 0 结果1
0 ^ 1 结果1
0 ^ 0 结果0
按位取反:~(一元运算符)
~1为0
~0为1
*/
class Test15_Bit{
public static void main(String[] args){
/*
4的二进制:0000 0100
4<<3:0 0100000
*/
System.out.println(4 << 3);//等价于4乘以2的3次方,4*8=32
/*
32的二进制:0010 0000
32>>4:0000 0010
*/
System.out.println(32 >>4);//等价于32除以2的4次方,32/16 =2
/*
-32的二进制:
原码:1010 0000
反码:1101 1111
补码:1110 0000
-32>>4:1111 1110
补码:1111 1110
反码:1111 1101
原码:1000 0010
*/
System.out.println(-32 >>4);
System.out.println(32 >>> 4);//和>>一样,左边补0
/*
-32的二进制:
原码:1000 0000 0000 0000 0000 0000 0010 0000
反码:1111 1111 1111 1111 1111 1111 1101 1111
补码:1111 1111 1111 1111 1111 1111 1110 0000
-32>>>4:0000 1111 1111 1111 1111 1111 1111 1110
最高位是0,是正数
*/
System.out.println(-32 >>> 4);
/*
32:0000 0000 0000 0000 0000 0000 0010 0000
25:0000 0000 0000 0000 0000 0000 0001 1001
32 & 25:0000 0000 0000 0000 0000 0000 0000 0000
*/
System.out.println(32 & 25);
/*
32:0000 0000 0000 0000 0000 0000 0010 0000
25:0000 0000 0000 0000 0000 0000 0001 1001
32 | 25:0000 0000 0000 0000 0000 0000 0011 1001
*/
System.out.println(32 | 25);
/*
32:0000 0000 0000 0000 0000 0000 0010 0000
25:0000 0000 0000 0000 0000 0000 0001 1001
32 | 25:0000 0000 0000 0000 0000 0000 0011 1001
*/
System.out.println(32 ^ 25);
/*
3:0000 0000 0000 0000 0000 0000 0000 0011
~3:1111 1111 1111 1111 1111 1111 1111 1100
补码:1111 1111 1111 1111 1111 1111 1111 1100
反码:1111 1111 1111 1111 1111 1111 1111 1011
原码:1000 0000 0000 0000 0000 0000 0000 0100 -4
*/
System.out.println(~3);
}
}
/*
运算符优先级:
(1)赋值类运算符是最低的,即赋值最后算
(2)条件运算符
(3)||-> &&-> |-> ^-> &
(4)比较运算符
(5)左移右移的位运算符
(6)算术运算符
乘、除、模高于加和减
(7)自增,自减,以及按位取反,非
(8).(面向对象用)和()
我们如果要准确的记忆每一种运算符的优先级是困难的。
我们遵循一个原则:
(1)表达式不要写太复杂,可以分为多行
(2)如果非要混合运算,那么先算的用()括起来
关于&,|,^,看左右两边的操作数是boolean值,还是整数,来决定是逻辑运算符还是位运算符。
*/
class Test16_Priority{
}
/*
交换两个变量的值
*/
class Test17_Swap{
public static void main(String[] args){
int x = 1;
int y = 2;
/*
通用的方案:适用于任意的数据类型
借助于第三个通样类型的临时变量
*/
int temp = x;//x变量中值就赋值给了temp temp = 1
x = y;//再把y中的值放到x中,x = 2
y = temp;//再把temp中的值赋值给y y=1
System.out.println("x = " + x);
System.out.println("y = " + y);
x = 1;
y = 2;
/*
方案二:只适用于int等整数类型
*/
x = x ^ y;
y = x ^ y;//(新的x) ^ 原来的y = (原来的x ^ 原来的y) ^ 原来的y = 原来的x (求不同)
x = x ^ y;//(新的x) ^ 新的y = (原来的x ^ 原来的y) ^ 原来的x = 原来的y
System.out.println("x = " + x);
System.out.println("y = " + y);
x = 1;
y = 2;
/*
方案三:只适用于int等整数类型
有风险,可能会溢出
*/
x = x + y;//有风险,可能会溢出
y = x - y;//(新的x) - 原来的y = (原来的x + 原来的y)- 原来的y = 原来的x
x = x - y;//(新的x) - 新的y = (原来的x + 原来的y) - 原来的x = 原来的y
System.out.println("x = " + x);
System.out.println("y = " + y);
/*
以下不推荐
*/
x = 1;
y = 2;
x = x * y;//风险更大
y = x / y;
x = x / y;
}
}
/*
1、定义一个int类型变量,保存年份,判断这个年份是否是闰年
注:判断一年是否是闰年的标准:
1)可以被4整除,但不可被100整除
2)可以被400整除
*/
class Test18_Exer{
public static void main(String[] args){
int year = 2000;
boolean result = year%4==0 && year%100!=0 || year%400==0;
System.out.println(year + (result?"是闰年":"不是闰年"));
}
}
//2、定义三个int类型的变量,x,y,z,随意赋值整数值,求最大值
class Test19_Exer{
public static void main(String[] args){
int x = 23;
int y = 34;
int z = 49;
//int max = x>=y ? x : y;//运行完这句max中存的是x与y中的最大值
//max = max >=z ? max : z;//用新的max与z比较
int max = (x>=y ? x : y) >= z ? (x>=y ? x : y) : z;
System.out.println("max = " + max);
}
}