Java包装类

Java语言是一个面向对象的语言,但是Java中的基本数据类型却是不面向对象的,这在实际使用时存在很多的不便(比如无法封装和类型相关的一些操作),为了解决这个不足,在设计类时为每个基本数据类型设计了一个对应的类进行代表,这样八个和基本数据类型对应的类统称为包装类(Wrapper Class)。这些类封装了对特定数据类型进行处理的操作。比如需要对char类型的数据进行操作就需要使用Character类型(每个包装类都封装了对所包装类型的常用操作)。

关于各种对象的操作的学习还是需要借助于JDK和源代码,这里就举几个例子。

1.所有的数字类型的包装类都封装了该类型的最大值和最小值
以Integer为例子,在Integer的源代码中:
@Native public static final int   MIN_VALUE = 0x80000000;
@Native public static final int   MAX_VALUE = 0x7fffffff;
这两个static final的属性就已经规定了Integer可以存储的数据的大小。
2.方便的类型转换
和C++对比,比如C++中用int和String进行转换的时候是使用stringstream对象或者调用使用库函数(boost库中的lexical_cast),
而java的包装类封装了类型转换的操作。实现了数据和方法的封装,这就是面向对象的优势(从这里也可以看出C++没有JAVA面向对象)。
以int和String的相互转换为例
int -> String
int i=12345;
String s="";
//第一种方法
s=i+"";
//i装箱为Integer之后调用Integer.toString然后就是String重载的+操作符,所以创建了2个String对象

//第二种方法
s=String.valueOf(i);
//String.valueOf(int i)源码
public static String valueOf(int i) {
    return Integer.toString(i);
}
//String.valueOf()对所有的对象内置类型都重载了,如果是Object就调用Object.toString()
public static String valueOf(boolean b) {
    return b ? "true" : "false";
}
public static String valueOf(Object obj) {
    return (obj == null) ? "null" : obj.toString();
}

String -> int
s="12345";
int i;
//第一种方法
i=Integer.parseInt(s);
//Integer.parseInt()就是专为String转int所设计的并且有不同重载版本,可以设定进制:
//源码
public static int parseInt(String s, int radix){
	......
}
public static int parseInt(String s) throws NumberFormatException {
    return parseInt(s,10);
}

//第二种方法
i=Integer.valueOf(s).intValue();
//源码
public static Integer valueOf(String s) throws NumberFormatException {
    return Integer.valueOf(parseInt(s, 10));
}
//parseInt返回的是int值,之后就是调用Integer.valueOf(int)
//Integer.intVaule就是获取Integer中所封装的int值了。
3.优化功能(对象池)
其实这个特点应当算是虚拟机的特点,但是如果不是对象的话虚拟机也无法实现这样的优化功能,这里用到的就是一个对象池的概念,在python中同样存在,另外啰嗦一句,与python相比Java的基本类型还不是对象(不继承自Object)而python中所有的对象都继承自Object。
//例子:
Integer i = 3;
//这句代码经过编译之后被编译器优化为:
Integer localInteger = Integer.valueOf(3);

可以看出装箱就是使用的valueOf,拆箱就是使用的intValue,(这里只是一Integer为例),这些都是编译器的任务。而真正执行Integer.valueOf(3)的时候是运行期了,看一下源码:
public static Integer valueOf(int i) {
    if (i >= IntegerCache.low && i <= IntegerCache.high)
        return IntegerCache.cache[i + (-IntegerCache.low)];
    return new Integer(i);
}
使用到了IntegerCache,而这个IntergerCache就是所谓的Integer的对象池。IntegerCache是Integer中的一个static的内部类,在JVM第一次载入Integer类的时候,就会加载IntegerCache类,而IntegerCache中使用static块进行初始化。所以第一次加载Integer类的时候就已经初始化好了IntegerCache类了。这一点是与python不同的python的小整数池一直都是在虚拟机内部的。

看源码:

public final class Integer extends Number implements Comparable<Integer> {
	...
	...
	...
	private static class IntegerCache {
        static final int low = -128;
        static final int high;
        static final Integer cache[];

        static {
            // high value may be configured by property
            int h = 127;
            String integerCacheHighPropValue =
                sun.misc.VM.getSavedProperty("java.lang.Integer.IntegerCache.high");
            if (integerCacheHighPropValue != null) {
                try {
                    int i = parseInt(integerCacheHighPropValue);
                    i = Math.max(i, 127);
                    // Maximum array size is Integer.MAX_VALUE
                    h = Math.min(i, Integer.MAX_VALUE - (-low) -1);
                } catch( NumberFormatException nfe) {
                    // If the property cannot be parsed into an int, ignore it.
                }
            }
            high = h;

            cache = new Integer[(high - low) + 1];
            int j = low;
            for(int k = 0; k < cache.length; k++)
                cache[k] = new Integer(j++);

            // range [-128, 127] must be interned (JLS7 5.1.7)
            assert IntegerCache.high >= 127;
        }

	    private IntegerCache() {}
	}
	...
	...
	...
}

从源码中可以看出,IntegerCache中所存储的是-128~127的Integer对象。另外注意IntegerCache中private构造函数。

本文仅以Integer类做为Java包装类学习的示例,基本思想相似,但是各个类都有区别,因为所处理的对象不同。


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值