美文网首页
一道面试题的回顾

一道面试题的回顾

作者: 有时右逝 | 来源:发表于2017-10-20 08:10 被阅读0次

前言

辞职休息了一个月,去了一次泰国,也疯够了。于是回来专心找工作。陆续去了一些公司参与面试,做了一些笔试题。有一道笔试题,我做错了。出乎我自己的意外。于是记录以吸取教训。

问题描叙

String s = null;
System.out.print("s="+s);

程序执行的结果是什么?是否会报错?

我的回答(错误)

考虑s为null, 字符串连接的时候,我认为 会调用s的toString() 方法。这样肯定出现空指针异常。
于是我写出答案:

  • 程序可以编译,但是运行时报异常。空指针异常。

正确答案

s=null

这真是让我很懵逼。居然可以执行。而且还是null 。

解决思路

这个问题可以拆分为三个小问题。

第一个问题

String s = null;
System.out.print(s);

结果输出为 null ,这里为何输出null .问题出在 pring函数上。定位该函数的源码,其中有这样的一段。

public void print(String s) {
        if (s == null) {
            s = "null";
        }
        write(s);
    }

很粗暴的判断。jdk的简单处理,有点让人失望。

第二个问题。

Integer i = null;
System.out.print(i);

结果输出是null. 查看函数源码

public void print(Object obj) {
        write(String.valueOf(obj));
    }

继续

public static String valueOf(Object obj) {
        return (obj == null) ? "null" : obj.toString();
    }

一切真相大白。

第三个问题。
就是我们的面试题目,这里也是相同的原因吗?
由于 + 是基本运算符,我们无法直接查看源码,了解其执行的逻辑。
这个只能去查询资料。最终的结论是 jvm 会对 + 进行优化。其执行逻辑如下:

String s = "a" + "b";
//等价于
StringBuilder sb = new StringBuilder();
sb.append("a");
sb.append("b");
String s = sb.toString();

因此 我们只需要去查看 append即可。

 public AbstractStringBuilder append(String str) {
        if (str == null)
            return appendNull();
        int len = str.length();
        ensureCapacityInternal(count + len);
        str.getChars(0, len, value, count);
        count += len;
        return this;
    }
private AbstractStringBuilder appendNull() {
        int c = count;
        ensureCapacityInternal(c + 4);
        final char[] value = this.value;
        value[c++] = 'n';
        value[c++] = 'u';
        value[c++] = 'l';
        value[c++] = 'l';
        count = c;
        return this;
    }

结果很明显。字符串执行 + 时,如果字符串为Null 最终添加的是 null 字符串。

总结

  • print函数对null的处理。

    • String 对象:直接判断是否为 null,如果为 null 给 null 对象赋值为"null"。
    • 非 String 对象:通过调用String.valueOf方法,如果是 null 对象,就返回"null",否则调用对象的toString方法。
  • 字符串相加( +) 对null的处理

    • jvm会将+ 优化为 StringBuilder来处理。如果为null 则添加 "null"

以上2点,最终的结果是

打印一个 null 对象而不会抛出异常

至于为何要如此,不知道jdk的作者是怎么想的。

参考

感谢 http://blog.xiaohansong.com/2016/03/13/null-in-java-string/

其他类似面试题

类似这类的面试题还有。例如

Integer a = 12; 
Integer b = 12; 
System.out.println(a == b);
Integer a = new Integer(12); 
Integer b = new Integer(12); 
System.out.println(a == b);
Integer a = 212; 
Integer b = 212; 
System.out.println(a == b);
Integer a = 212; 
int b = 212; 
System.out.println(a == b);

以上分别打印什么? 能正确回答的估计寥寥无几。

答案与分析http://m.blog.csdn.net/csummm4/article/details/20659363

相关文章

网友评论

      本文标题:一道面试题的回顾

      本文链接:https://www.haomeiwen.com/subject/eyjmuxtx.html