Нет исключения при приведении типа с нулем в java


String x = (String) null;

Почему в этом утверждении нет исключения?

String x = null;
System.out.println(x);

печати null. Но .toString() метод должен вызвать исключение нулевого указателя.

9 169

9 ответов:

вы можете null для любого ссылочного типа без получения каких-либо исключений.

println метод не бросает нулевой указатель, потому что он сначала проверяет, является ли объект null или нет. Если null, то он просто печатает строку "null". В противном случае он будет вызывать toString метод этого объекта.

добавление более подробной информации: внутренний вызов методов печати String.valueOf(object) метод ввод объекта. И в valueOf метод, эта проверка помогает избежать null указатель excpeiton:

return (obj == null) ? "null" : obj.toString();

для остальной части вашей путаницы, вызов любого метода на null объект должен бросить исключение нулевого указателя, если бы не особый случай.

вы можете null для любого ссылочного типа. Вы также можете вызвать методы, которые обрабатывают null в качестве аргумента, например,System.out.println(Object) делает, но вы не можете ссылаться на null значение и вызов метода на нем.

кстати, есть сложная ситуация, когда вы можете вызвать статические методы на null значения.

Thread t = null;
t.yield(); // Calls static method Thread.yield() so this runs fine.

Это дизайн. Вы можете бросить null к любому типу ссылки. В противном случае вы не сможете назначить его ссылочным переменным.

приведение нулевых значений требуется для следующей конструкции, где метод перегружен, и если null передается этим перегруженным методам, то компилятор не знает, как очистить неоднозначность, поэтому нам нужно ввести null в этих случаях:

class A {
  public void foo(Long l) {
    // do something with l
  }
  public void foo(String s) {
    // do something with s      
  }
}
new A().foo((String)null);
new A().foo((Long)null);

в противном случае вы не могли бы вызвать метод, который вам нужен.

Println(Object) использует String.valueOf()

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

Print(String) не нулевой чек.

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

как уже писали другие, вы можете привести null ко всему. Обычно вам это не нужно, вы можете написать:

String nullString = null;

не ставя бросили там.

но бывают случаи, когда такие броски имеют смысл:

a) если вы хотите убедиться, что вызывается определенный метод, например:

void foo(String bar) {  ... }
void foo(Object bar) {  ... }

тогда это будет иметь значение, если вы типа

foo((String) null) vs. foo(null)

b) если вы собираетесь использовать свою IDE для генерации кода; например, я как правило, написание модульных тестов, таких как:

@Test(expected=NullPointerException.class)
public testCtorWithNullWhatever() {
    new MyClassUnderTest((Whatever) null);
}

Я делаю TDD; это означает, что класс "MyClassUnderTest", вероятно, еще не существует. Записав этот код, я могу использовать свою IDE для первого создания нового класса; а затем создать конструктор, принимающий "любой" аргумент "из коробки" - IDE может понять из моего теста, что конструктор должен принимать ровно один аргумент типа Whatever.

Print:

печать объекта. Строка, производимая строкой.метод valueOf (Object) преобразуется в байты

ValueOf:

если аргумент null, то строка равна "null"; в противном случае, значение obj.toString() возвращается.

Он будет просто возвращать строку со значением "null", когда объект null.

Это очень удобно при использовании метода, который в противном случае был бы неоднозначным. Например: JDialog имеет конструкторы со следующими сигнатурами:

JDialog(Frame, String, boolean, GraphicsConfiguration)
JDialog(Dialog, String, boolean, GraphicsConfiguration)

мне нужно использовать этот конструктор, потому что я хочу установить GraphicsConfiguration, но у меня нет родителя для этого диалога, поэтому первый аргумент должен быть null. Используя

JDialog(null, String, boolean, Graphicsconfiguration) 

неоднозначно, поэтому в этом случае я могу сузить вызов, приведя null к одному из поддерживаемых типов:

JDialog((Frame) null, String, boolean, GraphicsConfiguration)

многие ответы здесь уже упоминал

вы можете привести null к любому ссылочному типу

и

Если аргумент равен null, то строка равна "null"

Я задался вопросом, где это указано, и посмотрел его спецификацию Java:

null ссылка всегда может быть приведен к любому ссылочному типу (§5.2, §5.3, §5.5).

если ссылка имеет значение null, преобразуется в строку "null" (четыре символа ASCII n, u, l, l).