说说关于String.valueOf的这个坑。java
public class TestString { public static void main(String[] args){ Object obj = null; System.out.println(String.valueOf(obj)); System.out.println(String.valueOf(null)); } }
这段代码,第一个输出“null”,没错,不是空对象null也不是空串“”,而是一个字符串!!包含四个字母n-u-l-l的字符串...this
第二个输出,咋一看没差异,可是,第二个输出,抛空指针异常了。指针
下面来分析分析缘由。code
先说第一个:对象
看第一个的源码实现:字符串
/** * Returns the string representation of the <code>Object</code> argument. * * @param obj an <code>Object</code>. * @return if the argument is <code>null</code>, then a string equal to * <code>"null"</code>; otherwise, the value of * <code>obj.toString()</code> is returned. * @see java.lang.Object#toString() */ public static String valueOf(Object obj) { return (obj == null) ? "null" : obj.toString(); }
源码很简单,若是对象为空,就返回字符串的"null"...不为空就调用toString方法。源码
再来讲第二个:string
第二个和第一个的不一样,是java对重载的不一样处理致使的。it
基本类型不能接受null入参,因此接受入参的是对象类型,以下两个:io
String valueOf(Object obj)
String valueOf(char data[])
这两个都能接受null入参,这种状况下,java的重载会选取其中更精确的一个,所谓精确就是,重载方法A和B,若是方法A的入参是B的入参的子集,则,A比B更精确,重载就会选择A。换成上面这两个就是,char[]入参的比object的更精确,由于object包含char[],因此String.valueOf(null)是用char[]入参这个重载方法。
看看这个方法的实现:
/** * Returns the string representation of the <code>char</code> array * argument. The contents of the character array are copied; subsequent * modification of the character array does not affect the newly * created string. * * @param data a <code>char</code> array. * @return a newly allocated string representing the same sequence of * characters contained in the character array argument. */ public static String valueOf(char data[]) { return new String(data); }
直接new String的,再看new String的实现:
/** * Allocates a new {@code String} so that it represents the sequence of * characters currently contained in the character array argument. The * contents of the character array are copied; subsequent modification of * the character array does not affect the newly created string. * * @param value * The initial value of the string */ public String(char value[]) { this.value = Arrays.copyOf(value, value.length); }
第12行,入参为null,null.length就报NPE了。
你们用的时候养成多看源码实现的好习惯,能够避免踩坑...