Java编程思想读书笔记——第三章:操作符

第三章 操作符

在最底层,Java中的数据是通过使用操作符来操作的

Java是建立在C++基础之上的,Java大部分和C++相似,但是也做了一些改进和简化

3.1 更简单的打印语句

静态导入一个小类库可以简化打印语句

练习1、分别使用简短的和正常的打印语句

public class E01_PrintStatements {   
    public static void main(String[] args) {     
        Date currDate = new Date();     
        System.out.println("Hello, it's: " + currDate);     
        print("Hello, it's: " + currDate);   
    } 
}

3.2 使用Java操作符

  • 加减乘除、正号负号、=等等
  • 几乎所有的操作符都只能操作基本类型
  • =、==、!=、可以操作所有的对象
  • String类支持 +、+=

3.3 优先级

最简单的加减乘除不用提了,而其他的逻辑运算符也差不多,编程中几乎不太会有这方面的问题,因为如果你写错会有提示的

3.4 赋值

1、基本数据类型的赋值就是直接存储了实际的数值,并不是引用

a = 1;
b = 2;
c = 3;

a = c;
b = c;

// 那么abc都为3,无论如何操作a和b,对c都没有任何影响

2、而在为对象赋值的时候,却不一样,持有了引用,只要引用一变,就都变

// 新建三个城市类,参数为该城市的人数
City cityA = new City(100);
City cityB = new City(200);
City cityC = new City(300);

cityA = cityC;
cityB = cityC;

cityA.number = 1000;

// cityA、cityB、cityC都持有“有300个人的城市”的引用
// cityA将人口变为1000,那么cityA、cityB、cityC的人数都变为了1000
// 而“有100个人的城市”、“有200个人的城市”将不会被引用,会被垃圾回收器自动清理

练习2:展示别名机制

class Integral {   
    float f; 
}  
 
public class E02_Aliasing {   
    public static void main(String[] args) {     
        Integral n1 = new Integral();     
        Integral n2 = new Integral();     
        n1.f = 9f;     
        n2.f = 47f;     
        print("1: n1.f: " + n1.f + ", n2.f: " + n2.f);     
        n1 = n2;     
        print("2: n1.f: " + n1.f + ", n2.f: " + n2.f);     
        n1.f = 27f;     
        print("3: n1.f: " + n1.f + ", n2.f: " + n2.f);   
    } 
}

3.4.1 方法调用中的别名问题

在方法中传递,并不是复制了一个副本,而是传了一个引用

某某方法通过参数中的这个引用操作了这个对象,改变的就是这个对象的值

class City {
    int number;
}

class CityManager {
    static void changeNumber(City city) {
        city.number = 250;
    }
}

class Main {
    public static void main(String[] args) {
        City cityA = new City();
        cityA.number = 100;
        CityManager.changeNumber(city);
        print("最终的城市人口数为:" + cityA.number);
    }    
}

// 最后的结果将会是250,changeNumber(city)这个方法会把整个对象的值改变了
// 初学者爱犯的错误:
// 认为只是将参数的值改了,改变后的值就只能在这个方法内使用
// 出了这个方法以后就又变到原来的值了
// 别问我为什么这么清楚,因为我以前就是这样认为的,哈哈哈~

练习3、展示方法调用时的别名机制

public class E03_Aliasing2 {   
    static void f(Integral y) { 
    y.f = 1.0f; 
    }   
    public static void main(String[] args) {     
        Integral x = new Integral();     
        x.f = 2.0f;     
        print("1: x.f: " + x.f);     
        f(x);    
        print("2: x.f: " + x.f);   
    } 
}

3.5 算术操作符

+、-、*、/、%、+=等等

练习4、编写一个计算速度的程序,时间和距离都是常量

public class E04_Velocity {   
    public static void main(String[] args) {     
        if(args.length < 2) {       
            System.err.println("Usage: java E04_Velocity distance time");                           
            System.exit(1);     
        }     
        float distance = Float.parseFloat(args[0]);     
        float time = Float.parseFloat(args[1]);     
        System.out.print("Velocity = ");     
        System.out.print(distance / time);     
        System.out.println(" m/s");   
    } 
}

3.5.1 一元加、减操作符

正号和负号

3.6 自动递增递减

++,--,一种是前缀,一种是后缀,比较简单不说啦

3.7 关系操作符

生成boolean类型的值,<、>、>=、<=、==、!=

3.7.1 测试对象的等价性

==和!=比较的是对象的引用

City cityA = new City(100);
City cityB = new City(100);

cityA == cityB

// 这个值肯定返回的是false;
// 两个城市的人口都是100,并不能确定他们就是同一个城市

比较内容是否相同:

  • 基本类型直接使用==
  • 而其他对象必须使用equals来比较内容是否相同
  • equals的默认行为是比较引用,如果自定义的类,我们想要比较内容是否相等,得去重写equals方法
  • 大多数类库都实现了equals()方法,用来比较对象的内容,而不是比较对象的引用

练习5、创建Dog类,拥有Stirng类型的name和says,并创建两个对象,赋予它们相应的值并打印出来

class Dog {   
    String name;   
    String says; 
} 
 
public class E05_Dogs {   
    public static void main(String[] args) {     
        Dog dog1 = new Dog();     
        Dog dog2 = new Dog();     
        dog1.name = "spot";      
        dog1.says = "ruff!";     
        dog2.name = "scruffy";   
        dog2.says = "wurf!";     
        System.out.println(dog1.name + " says " + dog1.says);                             
        System.out.println(dog2.name + " says " + dog2.says);   
    } 
} 

练习6、在练习5的基础上,测试==和equals()方法来比较结果

public class E06_DogsComparison {   
    static void compare(Dog dog1, Dog dog2) {     
        print("== on top references: " + (dog1 == dog2));     
        print("equals() on top references: " + dog1.equals(dog2));             
        print("== on names: " + (dog1.name == dog2.name));     
        print("equals() on names: " + dog1.name.equals(dog2.name));                                                 
        print("== on says: " + (dog1.says == dog2.says));     
        print("equals() on says: " + dog1.says.equals(dog2.says));   
    }   
    public static void main(String[] args) {     
        Dog dog1 = new Dog();     
        Dog dog2 = new Dog();     
        Dog dog3 = dog1;  // "Aliased" reference     
        dog1.name = "spot";    
        dog1.says = "ruff!";     
        dog2.name = "scruffy"; 
        dog2.says = "wurf!";     
        print("Comparing dog1 and dog2 objects...");     
        compare(dog1, dog2);                     
        print("\nComparing dog1 and dog3 objects...");     
        compare(dog1, dog3);         
        print("\nComparing dog2 and dog3 objects...");     
        compare(dog2, dog3);   
    } 
}

// 运行结果显而易见:
// compare(dog1, dog3)返回的都是true
// 剩下两个返回的结果都是false

3.8 逻辑操作符

与或非,&&、||、!

练习7、模拟抛硬币的结果

public class E07_CoinFlipping {   
    public static void main(String[] args) {     
        Random rand = new Random(47);     
        boolean flip = rand.nextBoolean();     
        System.out.print("OUTCOME: ");     
        System.out.println(flip ? "HEAD" : "TAIL");   
    } 
} 

3.8.1 短路

逻辑运算的时候如果前面的为false,后面的就不执行下去了,这个很好理解

3.9 直接常量

int、char、byte、short、long、float、double都可以用直接常量

练习8、用十六进制和八进制计数法来操作long值

public class E08_LongLiterals {   
    public static void main(String[] args) {     
        long l1 = 0x2f; // Hexadecimal (lowercase)     
        print("l1: " + Long.toBinaryString(l1));     
        long l2 = 0X2F; // Hexadecimal (uppercase)     
        print("l2: " + Long.toBinaryString(l2));     
        long l3 = 0177; // Octal (leading zero)     
        print("l3: " + Long.toBinaryString(l3));   
    } 
}

3.9.1 指数计数法

简单的说,在Java中,e表示10的幂次

练习9、分别显示用float和double指数计数法所能表示的最大和最小的数字

public class E09_MinMaxExponents {   
    public static void main(String[] args) {     
        print("Float MIN: " + Float.MIN_VALUE);     
        print("Float MAX: " + Float.MAX_VALUE); 
        print("Double MIN: " + Double.MIN_VALUE);     
        print("Double MAX: " + Double.MAX_VALUE);   
    } 
} 

3.10 按位操作符

二进制位的操作,与或非异或,和逻辑运算符的区别是只使用了一个符号,并且不会短路

练习10、二进制的一个操作

public class E10_BitwiseOperators {   
    public static void main(String[] args) {     
        int i1 = 0xaaaaaaaa;     
        int i2 = 0x55555555;     
        print("i1 = " + Integer.toBinaryString(i1));     
        print("i2 = " + Integer.toBinaryString(i2));     
        print("~i1 = " + Integer.toBinaryString(~i1));     
        print("~i2 = " + Integer.toBinaryString(~i2));     
        print("i1 & i1 = " + Integer.toBinaryString(i1 & i1));     
        print("i1 | i1 = " + Integer.toBinaryString(i1 | i1));     
        print("i1 ^ i1 = " + Integer.toBinaryString(i1 ^ i1));     
        print("i1 & i2 = " + Integer.toBinaryString(i1 & i2));     
        print("i1 | i2 = " + Integer.toBinaryString(i1 | i2));     
        print("i1 ^ i2 = " + Integer.toBinaryString(i1 ^ i2));   
    } 
} 

3.11 移位操作符

操作对象也是二进制的位,只能处理整型

练习11、右移

public class E11_SignedRightShift {   
    public static void main(String[] args) {     
        int i = 0x80000000;     
        print(Integer.toBinaryString(i));     
        i >>= 1;  print(Integer.toBinaryString(i));     
        i >>= 1;  print(Integer.toBinaryString(i));     
        i >>= 1;  print(Integer.toBinaryString(i));     
        i >>= 1;  print(Integer.toBinaryString(i));     
    } 
} 
/* Output: 
10000000000000000000000000000000 
11000000000000000000000000000000 
11100000000000000000000000000000 
11110000000000000000000000000000 

练习12、先左移再右移

练习13、二进制形式显示char类型的值

这俩略了,差不多就这个意思,弄了半天,主要是用了Integer.toBinaryString()方法

3.12 三元操作符 if-else

boolean ? value1 : value2

使用三元操作符代码会更简洁,但是可读性有点差,选择使用的时候请考虑

3.13 字符串操作符 + 和 +=

如果表达式以字符串开头,那么后续操作数都必须是字符串型,编译器会自动转换

3.14 使用操作符时常犯的错误

没啥说的,多注意吧

3.15 类型转换操作符

基本类型可以相互转换,所属类型可以相互转换

3.15.1 截尾和舍入

默认总会截尾,想要舍入使用Math中的round()方法

3.16 Java没有sizeof

Java不必考虑移植的问题

3.17 操作符小结

boolean的运算十分有限,只能true或者false

char、byte、short中,只要进行算术运算返回的都是int结果,必须将其转换回原来的类型

练习14、编写一个接受两个字符串参数的方法

3.18 总结

没啥说的啦,哈哈哈~

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值