Как избежать исключений NullPointerExceptions из toString из hashmap

Я пытаюсь избежать NullPointerException в коде, который пытается сравнить строку из HashMap.

HashMap хорошо определен, но может быть или не быть соответствующей записи в HashMap, поэтому я полагаю, что это может быть то, откуда может исходить мой NPE и связанное с ним предупреждение Android Studio.

Мой код:

if (region_ids !=null && source_region != null && selected_id != null) {
    if (source_region.equals("it") && region_ids.containsKey("it") && !selected_id.equals(region_ids.get("it").toString())) {
        // Do stuff for mismatched region
    }
}

Где region_ids это HashMap.

Достаточно ли я делаю, чтобы предотвратить NullPointerExceptions?

Если да, то почему Android Studio по-прежнему выдает мне предупреждение в среде IDE?

(Обратите внимание, что тег Android-Studio включен намеренно из-за того, что последняя часть этого вопроса относится к AS.)


Обновлять

Основываясь на комментарии Code-Apprentice и ответе Носяры, теперь у меня есть следующие два варианта оператора if, но я все еще получаю предупреждение NPE о методе toString():

if ( region_ids_string != null && spin_region_id != null && source_region != null && selected_id != null && assoc_ids != null) {
    if ( region_ids_string.size() > spin_region_id.getSelectedItemPosition()) {
        if (source_region.equals("com_mx") && assoc_ids.get("com_mx") != null && assoc_ids.containsKey("com_mx") && !selected_id.equals(assoc_ids.get("com_mx").toString())) {
                return true;
        } else if ("com_au".equals(source_region) && assoc_ids.containsKey("com_au") && assoc_ids.get("com_au") != null && !assoc_ids.get("com_au").toString().equals(selected_id)) {
            return true;
        } else {
            return false;
        }
    } else {
        return false;
    }
} else {
    return false;
}

Итак, я считаю, что сейчас проверяю null, "", и существует ли Key в HashMap, но AS по-прежнему считает, что операторы могут генерировать NPE...

Я не знаю, откуда берется NPE, но основные шаги, чтобы понять это, одинаковы. Разбейте оператор IF на части и начните распечатывать. Вы, вероятно, найдете что-то странное. И вы уверены, что это то, откуда исходит ваш NPE?

Joseph Larson 16.05.2019 20:41

У меня проблема в том, что я не могу воспроизвести ошибку сам. Я вижу, что об этом сообщается только в консоли разработчика Google Play (но обфускация/деобфускация в настоящее время теряет детали!). Это и тот факт, что я вижу предупреждение в IDE. Так что разбирать его по пунктам if за пунктом if на данный момент проблема сама по себе. Если также хотелось бы знать, правильно ли я использую containsKey() в этом контексте.

Fat Monk 16.05.2019 21:10

«Достаточно ли я делаю, чтобы предотвратить NullPointerExceptions?» - нет. Не видя всего вашего кода, возможно, что region_ids.get("it") дает нуль, делая region_ids.get("it").toString() генерировать NPE, если используемая вами реализация карты допускает нулевые значения.

Not a JD 16.05.2019 21:20

Я думал, что region_ids.containsKey("it") would ensure that region_ids.get("it")` не будет null'. Is that not the case? If not, what is the best way to check that? I tried region_ids.get("it") != null` в тесте if вместо containsKey, но все равно получил предупреждение в IDE.

Fat Monk 16.05.2019 21:26

"Перед вышеизложенным я также проверяю..." Пожалуйста, покажите код, который идет с этим словесным объяснением.

Code-Apprentice 16.05.2019 21:40

@FatMonk Обратите внимание, что если вы сделаете region_ids.put("it", null);, то region_ids.containsKey("it") вернет true, но region_ids.get("it") будет null. так что ваше предположение неверно.

Code-Apprentice 16.05.2019 21:41

@FatMonk «Я попробовал region_ids.get("it") != null` в тесте if вместо containsKey, но все равно получил предупреждение в IDE». Вам нужны обе проверки, потому что они проверяют разные вещи.

Code-Apprentice 16.05.2019 21:42

Является ли region_ids.put("it","") эквивалентом `region_ids.put("it",null)? Я, вероятно, запутался здесь, но я думал, что NullPointerException означает, что указатель не указывает ни на что, а не указывает на что-то со значением null. Таким образом, объект может иметь значение null, но если объект не существует, то любой указатель на него будет указывать на то, что ничего не равно null....

Fat Monk 16.05.2019 22:23
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
В компьютерном программировании биты играют важнейшую роль в представлении и манипулировании данными на двоичном уровне. Побитовые операции...
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Приходилось ли вам сталкиваться с требованиями, в которых вас могли попросить поднять тревогу или выдать ошибку, когда метод Java занимает больше...
Полный курс Java для разработчиков веб-сайтов и приложений
Полный курс Java для разработчиков веб-сайтов и приложений
Получите сертификат Java Web и Application Developer, используя наш курс.
1
8
87
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Если вы перевернете условие с константой слева, вы автоматически проверите его на NULL. Вот так:

if ("it".equals(source_region) && 
region_ids.containsKey("it") && 
!(region_ids.get("it").toString().equals(selected_id))) {
    // Do stuff for mismatched region
}

Ооо, интересное предложение. Всегда ли так? Не могли бы вы объяснить немного больше, как это работает, потому что они могут быть действительно полезными.

Fat Monk 16.05.2019 22:27

Теперь я попробовал это, и Android Studio по-прежнему предупреждает меня о методе toString(). Конечно, должен быть способ проверки, чтобы сделать использование этого метода безопасным.

Fat Monk 23.05.2019 20:19

Другие вопросы по теме