这篇是常用 API 的结束了, 写完的话可以继续往后复习了.
1. 基本类型包装类的介绍与相关代码实现
对于数据包装类的特点就是可以将基本数据类型与字符串来回切换, 接下来我会通过介绍 Integer 类的形式, 来代表大部分的基本类型包装类的知识点, 原因是其余的包装类的使用与 Integer 类有 90% 的形式都是一样的.
- public class Demo1 {
- public static void main(String[] args) {
- function();
- }
- public static void function() {
- int i=Integer.parseInt("233"); // 该方法用于将字符串转换为 int 型!!!
- // 字符串必须为数字格式的
- System.out.println(i);
- }
- }
结果: 233
- public class Demo1 {
- public static void main(String[] args) {
- function1();
- }
- public static void function1() {
- int i=Integer.parseInt("123",4); // 该方法用于将指定进制数转换为十进制数
- System.out.println(i);
- }
- }
结果: 27
- public class Demo1 {
- public static void main(String[] args) {
- function2();
- }
- public static void function2() {
- String s=Integer.toString(5); // 通过调用静态方法将基本数据类型转换为字符串
- System.out.println(s+1);
- int i=5;
- String a=i+" "; // 这种方式更为简单粗暴, 但似乎和我们的 Integer 类没啥关系
- System.out.println(a);
- }
结果: 51
- 5
- public class Demo1 {
- public static void main(String[] args) {
- function3();
- }
- public static void function3() {
- String s=Integer.toString(155,2); // 将 int 型数转换为指定进制并返回字符串
- System.out.println(s);
- }
- }
结果: 10011011
这里我对于这些方法的总结看起来或许会因为没有文字介绍而显得令人很难受, 但其实我都是将具体文字写在代码中的, 由于这些方法的调用都极为简单, 所以我就不一一详细介绍了.....
2. JAVA 的自动装箱与自动拆箱
java 的自动拆箱与自动装箱功能是在 jdk 1.5 之后才引入的新的功能.
何为自动拆箱与自动装箱嘞?
我还是现将概念扔在最开始的地方吧, 总觉得在讲解中穿插概念, 会造成一些重要概念的遗漏...
自动装箱: 基本数据类型, 直接转变为引用数据类型.
自动拆箱: 引用数据类型转变为基本数据类型.
下面我将通过一些代码以及文字来对其进行解释.
自动装箱:
Integer in=1;
我想问一下, 我们平常是否见过这种直接可以给对象赋值的操作, 或者在我们的印象中这种情况是否合理. 我们都知道对象中存储的是堆内存中的地址, 所以这其中一定有什么步骤被隐藏了.
- Integer in=1;
- Integer in=Integer.valueOf(1);
下面一行代码便是这个过程的完整代码. 也就是说并不存在所谓的给对象赋值这种神仙操作, 因为 valueOf() 方法最终返回的还是一个 Integer 类的对象.
这便是实现了自动装箱的概念: 将基本数据类型直接转换为引用数据类型.
自动拆箱:
- public class Demo2 {
- public static void main(String[] args) {
- Integer in=1;
- int i=in+1;
- System.out.print(i+" "); System.out.println(in);
} } 结果: 2 1
这里又出现了一些有违我们以往的所学, 一个引用数据类型怎么可能与一个基本数据类型进行加减法的运算嘞, 并且我们输出的 in 不是一个对象吗? 所以说这里边就又有门道啦.
- System.out.println(in);
- System.out.println(in.intValue()); // 这两句话是等价的
- int i=in+1; // 这两句话是等价的
- int i=in.intValue()+1;
若是看代码还是有些模糊的话, 那我就再说一下 intValue() 方法的一些特点吧.
这是 API 中的介绍很明显通过这个方法就实现了自动拆箱: 将引用数据类型直接转为基本数据类型.
再通过比较的方法来加深理解吧!!!
- public class Demo2 {
- public static void main(String[] args) {
- Integer in=500;
- Integer in1=500; // 这两行边都是自动装箱啦
- System.out.println(in==in1);
- System.out.println(in.equals(in1)); // 这里是自动拆箱
- }
- }
结果: false
true
首先我们应该清楚 equals 方法是可以重写的, 恰巧在 Integer 类中又重写了这个方法, 所里这里比较的是值而不是地址, 那么 "==" 号嘞?
一定要记住两个对象比较的是地址.
- public class Demo2 {
- public static void main(String[] args) {
- Integer in2=127;
- Integer in3=127;
- System.out.println(in2==in3);
- System.out.println(in2.equals(in3));
- }
- }
结果: true
true
这里还有个比较奇特的东西, 感觉考试会出所以就分析一下吧.
在包装类创建的过程中, 若是数值小于 128JVM 便会认为不需要创建对象, 所以这里比较的都是数值的大小.
感觉很清楚了, 哈哈.
3.System 类的相关方法及使用
这里我就不用代码来介绍了总感觉不是太过重要, 若是加代码的话, 有种凑字数的感觉..
1.exit(int ) 退出当前虚拟机, 所有程序停止, 并且非 0 表示异常终止.
2.gc() 命令 JVM 在内存中回收对象的垃圾, 多用于匿名类之类的, 这种用一次就不用了, 但它还存在与堆内存中的.
3.getProperties() 获取当前系统的信息.
4.arraycopy(Object src, int srcPos, Object dest, int destPos, int length) 复制一个数组, 可以从指定索引处开始, 指定索引出结束.
src: 源数组 srcPos: 从原数组复制的起始索引 dest: 目标数组
destPos: 目标数组的起始索引 length: 复制的长度
4.BigInteger 类的介绍
该类主要用于大数运算, 即通过将那些我们无法以 long 型存入的数据, 以 String 等类型存入, 帮助我们完成计算.
对于该类, 我会简要介绍一下如何通过该类的一些方法来做到四则运算.
1. 加法 通过对象. add 的方式实现. 返回值为 BigInteger 类型.
2. 减法 通过对象. subtract 的方式实现. 返回值为 BigInteger 类型.
3. 乘法 通过对象. multiply 的方式实现. 返回值为 BigInteger 类型.
4. 除法 通过对象. divide 的方式实现. 返回值为 BigInteger 类型. 注意方法参数列表均为 Integer 类型对象.
5.BigDecimal 类的介绍
首先我们先介绍一下为什么要使用这个类.
通过代码来介绍吧..
- public class Demo1 {
- public static void main(String[] args) {
- function();
- }
- public static void function() {
- System.out.println(0.01+0.09);
- System.out.println(0.99-0.91);
- System.out.println(0.5*0.01);
- }
- }
结果:
- 0.09999999999999999
- 0.07999999999999996
- 0.005
这个答案是不是有违常理呀!!
我来解释一下吧.. 其实我们都知道数据在计算机中都是需要先转换为二进制的, 并且 float 类型以及 double 类型在转换时使用正常转换方式不一样的.
正常的转换方式: 我们以 9 为例子来说明吧.
9/2 余 1 4/2 余 0 2/2 余 0 1/2 余 1 所以最后转成的二进制数是 1001
那若是 0.9 嘞? 算法如下:
0.9*2=1.8 取出 0.8 1
0.8*2=1.6 取出 0.6 1
0.6*2=1.2 取出 0.2 1
0.2*2=0.4 取出 0.4 0
...... 一直这样算直到没有小数位置.
但是除非你取出的是 0.5 否则很难就保证精度准确地, 这也是为啥第三个输出的是正确的. 并且还应该了解计算机对于 float 类型数据的有效数位是 24, 对于 double 类型数据的有效数位是 52, 因为计算机忽略掉了 24 位或者是 52 位之后的数所以误差也就来了...
所以我们需要通过 BigDecimal 类来解决掉这些问题. 好现在来介绍 BigDecimal 完成四则运算的方法吧.
我会将加法, 减法, 乘法的代码写到一起, 然后将除法的代码隔离出来, 作为一个特例.
- import java.math.BigDecimal;
- public class Demo1 {
- public static void main(String[] args) {
- function1();
- function2();
- function3();
- }
- public static void function1() {
- BigDecimal b1=new BigDecimal("0.01");
- BigDecimal b2=new BigDecimal("0.09");
- BigDecimal b3=b1.add(b2);
- System.out.println(b3); // 加法
- }
- public static void function2() {
- BigDecimal b1=new BigDecimal("0.01");
- BigDecimal b2=new BigDecimal("0.09");
- BigDecimal b3=b1.multiply(b2); // 乘法
- System.out.println(b3);
- }
- public static void function3() {
- BigDecimal b1=new BigDecimal("0.01");
- BigDecimal b2=new BigDecimal("0.09");
- BigDecimal b3=b1.subtract(b2); // 减法
- System.out.println(b3);
- }
- }
结果: 0.01
- 0.009
- -0.08
对于除法的总结:
- import java.math.BigDecimal;
- public class Demo1 {
- public static void main(String[] args) {
- function1();
- function();
- }
- public static void function1() {
- BigDecimal b1=new BigDecimal("0.58");
- BigDecimal b2=new BigDecimal("0.2");
- BigDecimal b3=b1.divide(b2);
- System.out.println(b3);
- }
- public static void function() {
- BigDecimal b1=new BigDecimal("0.5832");
- BigDecimal b2=new BigDecimal("0.2333");
- BigDecimal b3=b1.divide(b2,6,BigDecimal.ROUND_HALF_UP );
- System.out.println(b3);
- }
- }
结果: 2.9
2.499876
着重对 function() 进行介绍
divide(BigDecimal divisor, int scale, RoundingMode roundingMode)
BigDecimal divisor: 指的是被除数
int scale: 指的是保留几位小数
RoundingMode roundingMode: 指的是保留模式......
其实到最后还有一些东西, 就是对于 BigDecimal 类是否存在自动装箱与拆箱的思考, 我没有写出来, 我会自己把它搞懂得 (哈哈)..
6. 结束
在做总结的过程中, 其实也不算很枯燥, 只是一直会不断发现新的问题, 我对于某些地方的总结真的是还不够, 但是仅仅通过本篇我便清楚的了解了自动装箱与自动拆箱以及数据精度受损的真正原因... 在解决问题的过程中我是享受其中的.
来源: https://www.cnblogs.com/roseneverdie/p/10561638.html