字符串构造函数与 null 值

10

为什么使用空值初始化String (String)构造函数会导致编译时错误?我认为有两个以上的构造函数接受Object类型参数,当以null值初始化时,它不知道从哪里开始。我想知道是否还有其他原因。

String s = new String(null); // compile time error


StringBuffer sb = new StringBuffer(null); // no error

当您尝试运行它时,StringBuffer 应该会出现 NullPointerException(当然,这并不是重点)。 - BoltClock
1
请查看以下网址:https://dev59.com/JHI_5IYBdhLWcg3wDOrW - pingw33n
4个回答

12

通常情况下,当调用一个可能有多个重载版本的构造函数或方法时,Java会选择最具体的构造函数或方法。第15.12.2节的Java语言规范详细解释了这一点。

假设你有两个重载的方法,像这样:

public void method(Object o) {
    // ...
}

public void method(String s) {
    // ...
}
当您调用method(null)时,这两种方法都适用。Java会选择最具体的方法,即在本例中接受String参数的第二个方法,因为String是比Object更具体的类型。
然而,有时无法确定最具体的构造函数或方法。如果我们查看只接受一个参数的String类的构造函数:
String(byte[] bytes)
String(char[] value)
String(String original)
String(StringBuffer buffer)
String(StringBuilder builder)

请注意,byte[]char[]StringStringBufferStringBuilder 这些类型之间没有层次关系,因此无法说其中一个构造函数比其他构造函数更具体。所以,Java编译器不知道选择哪个构造函数,会给出错误提示。


11
因为编译器无法确定调用哪个构造函数。可以在这里看到,它有多少个一参数构造函数。 [已编辑] 你说,如果有其他原因。那么何不自己试一下。像这样做些什么,
byte[] b = null;
String s = new String(b); // complier should be fine with this

char[] c = null;
String s = new String(c); // complier should be fine with this

.... // you can try other constructors using similar approach.

我认为是这样,但我想知道是否还有其他原因。我现在正在编辑我的问题。 - user467871

3
仅为解决方案增加更多的清晰度:
以这个例子为例:
public class Test {
public Test(Object obj) {
    System.out.println("Object");
}
public Test(String obj) {
    System.out.println("String");
}
public static void main(String[] args) {
    new Test(null);
}

}

如果可用相同类型的构造函数,则编译器将选择最具体的构造函数,因此不会引发任何编译时错误。但是,如果我更改类为:

public class Test {
public Test(Long lg){
    System.out.println("Long");
}
public Test(Object obj) {
    System.out.println("Object");
}
public Test(String obj) {
    System.out.println("String");
}
public static void main(String[] args) {
    new Test(null);
}
}

这将会引发编译时错误。因为涉及到两个不同的构造函数层次结构,编译器无法做出决策。一个层次结构是:Object-->String,另一个是Object-->Long,所以没有办法选择Long或String类型的构造函数。


1

String有许多构造函数。它们都可以使用null。

编辑:在Java 6中,String有5个一参数构造函数。感谢BoltClock和Adeel Ansari!


1
它有超过2个构造函数。 - BoltClock
1
在Java 6中,String类有5个单参数构造函数。 - Adeel Ansari

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接