Избегать! = Нулевые заявления

localhost, похоже, отлично работает в моем эмуляторе при запуске, а затем я начал получать отказ от отказа в подключении. Я использовал 127.0.2.2 из браузера эмулятора, и он работал, и когда я использовал это в своем приложении для Android в эмуляторе, он снова начал показывать соединение отказалось от проблемы.

, тогда я сделал ifconfig, и я использовал ip 192.168.2.2, и он отлично работал

3854
задан 28 revs, 23 users 12% 17 April 2018 в 17:15
поделиться

17 ответов

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

Для помещения этого иначе существует два экземпляра, где пустая проверка подходит:

  1. , Где пустой указатель является допустимым ответом с точки зрения контракта; и

  2. , Где это не допустимый ответ.

(2) легко. Или используйте assert операторы (утверждения) или позвольте отказ (например, NullPointerException). Утверждения являются высоко недогруженной опцией Java, которая была добавлена в 1,4. Синтаксис:

assert <condition>

или

assert <condition> : <object>

то, где <condition> булево выражение и <object>, является объектом, чей toString() вывод метода будет включен в ошибку.

assert оператор бросает Error (AssertionError), если условие не верно. По умолчанию Java игнорирует утверждения. Можно включить утверждения путем передачи опции -ea JVM. Можно включить и отключить утверждения для отдельных классов и пакетов. Это означает, что можно проверить код с утверждениями при разработке и тестировании, и отключить их в продуктивной среде, хотя мое тестирование не показало рядом ни с каким влиянием производительности от утверждений.

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

(1) немного более твердо. Если Вы не имеете никакого контроля над кодом, Вы звоните тогда, Вы застреваете. Если пустой указатель является допустимым ответом, необходимо проверить на него.

, Если это - код, которым Вы действительно управляете, однако (и это часто имеет место), тогда это - другая история. Избегайте использования аннулирует как ответ. С методами, которые возвращают наборы, это легко: возвратите пустые наборы (или массивы) вместо пустых указателей в значительной степени все время.

С ненаборами это могло бы быть более твердо. Рассмотрите это как пример: если у Вас есть эти интерфейсы:

public interface Action {
  void doSomething();
}

public interface Parser {
  Action findAction(String userInput);
}

, где Синтаксический анализатор берет необработанный ввод данных пользователем и находит, что что-то делает, возможно, при реализации интерфейса командной строки для чего-то. Теперь Вы могли бы сделать контракт, что он возвращает пустой указатель, при отсутствии соответствующих мер. Это приводит пустой указатель, проверяющий, что Вы говорите о.

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

public class MyParser implements Parser {
  private static Action DO_NOTHING = new Action() {
    public void doSomething() { /* do nothing */ }
  };

  public Action findAction(String userInput) {
    // ...
    if ( /* we can't find any actions */ ) {
      return DO_NOTHING;
    }
  }
}

Сравните:

Parser parser = ParserFactory.getParser();
if (parser == null) {
  // now what?
  // this would be an example of where null isn't (or shouldn't be) a valid response
}
Action action = parser.findAction(someInput);
if (action == null) {
  // do nothing
} else {
  action.doSomething();
}

к [1 136]

ParserFactory.getParser().findAction(someInput).doSomething();

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

Однако возможно, для findAction () метод совершенно уместно выдать Исключение со значимым сообщением об ошибке - особенно в этом случае, где Вы полагаетесь на ввод данных пользователем. Для findAction метода было бы намного лучше выдать Исключение, чем для вызывающего метода аварийно завершиться с простым NullPointerException без объяснения.

try {
    ParserFactory.getParser().findAction(someInput).doSomething();
} catch(ActionNotFoundException anfe) {
    userConsole.err(anfe.getMessage());
}

Или если Вы думаете, механизм попытки/выгоды слишком ужасен, а не Не Сделайте Ничего, что Ваше действие по умолчанию должно предоставить обратную связь пользователю.

public Action findAction(final String userInput) {
    /* Code to return requested Action if found */
    return new Action() {
        public void doSomething() {
            userConsole.err("Action not found: " + userInput);
        }
    }
}
2559
ответ дан 13 revs, 11 users 77% 17 April 2018 в 17:15
поделиться
  • 1
    В целом, если Вы используете ARC, и Ваши IBOutlets слабы, все разгружено, когда представление разгружено. Но без ARC и с сильным (сохраняют) IBOutlets (например, если Вы добавляете и удаляете их динамично из представления), Вы хотите выпустить их внутри viewDidUnload. Однако Вы хотите выпустить их также в Вашем dealloc методе. Для удаления двуличности кода Вы просто называете viewDidUnload от dealloc. Необходимо поместить его там всегда потому что it' s не названный автоматически, когда контроллер представления выпущен. – Sulthan 20 October 2011 в 17:40

Ничего себе, я почти очень не хочу добавить другой ответ, когда у нас есть 57 различных способов рекомендовать эти NullObject pattern, но я думаю, что некоторые люди, заинтересованные этим вопросом, хотели бы знать, что существует предложение по таблице для Java 7 для добавления "пустая безопасная обработка" — оптимизированный синтаксис для if-not-equal-null логики.

пример, данный Alex Miller, похож на это:

public String getPostcode(Person person) {  
  return person?.getAddress()?.getPostcode();  
}  

?. средства только разыменовывают левый идентификатор, если это не является пустым, иначе оцените остаток от выражения как null. Некоторые люди, как член Отряда Java Dick Wall и эти избиратели в Devoxx действительно любят это предложение, но также существует оппозиция, на том основании, что это на самом деле поощрит больше использования null как значение сигнальной метки.

<час>

Обновление: официальное предложение по пустому безопасному оператору в Java 7 было отправлено под Монета Проекта. синтаксис немного отличается, чем пример выше, но это - то же понятие.

<час>

Обновление: пустое безопасное предложение по оператору не превращало его в Монету Проекта. Так, Вы не будете видеть этот синтаксис в Java 7.

229
ответ дан 5 revs, 3 users 82% 17 April 2018 в 17:15
поделиться

Везде, куда Вы передаете массив или Вектор, инициализируете их к пустым вместо пустого указателя. - Этот способ, которым можно избежать большой проверки пустой указатель и все хорошо:)

public class NonNullThing {

   Vector vectorField = new Vector();

   int[] arrayField = new int[0];

   public NonNullThing() {

      // etc

   }

}
5
ответ дан 2 revs, 2 users 73%Stuart Axon 17 April 2018 в 17:15
поделиться

Только для этой ситуации -

Не проверка, если переменная является пустой прежде, чем вызвать, равняется методу (строка сравнивают пример ниже):

if ( foo.equals("bar") ) {
 // ...
}

приведет к NullPointerException, если foo не будет существовать.

можно избежать этого при сравнении Вашего String с как это:

if ( "bar".equals(foo) ) {
 // ...
}
175
ответ дан 3 revs, 3 users 68% 17 April 2018 в 17:15
поделиться

Если нулевые значения не позволяются

, Если Ваш метод называют внешне, запустите с чего-то вроде этого:

public void method(Object object) {
  if (object == null) {
    throw new IllegalArgumentException("...");
  }

Затем в остальной части того метода, Вы будете знать, что object не является пустым.

, Если это - внутренний метод (не часть API), просто документ, что это не может быть пустым, и вот именно.

Пример:

public String getFirst3Chars(String text) {
  return text.subString(0, 3);
}

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

, Если пустой указатель позволяется

, Это действительно зависит. Если находят, что я часто делаю что-то вроде этого:

if (object == null) {
  // something
} else {
  // something else
}

, Таким образом, я перехожу и делаю две совершенно других вещи. Нет никакого ужасного фрагмента кода, потому что я действительно должен сделать две разных вещи в зависимости от данных. Например, я должен работать над входом, или я должен вычислить хорошее значение по умолчанию?

<час>

на самом деле редко для меня использовать идиому" if (object != null && ...".

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

303
ответ дан 2 revs, 2 users 90% 17 April 2018 в 17:15
поделиться
  • , Если Вы рассматриваете, объект не должен быть пустым (или это - ошибка), используют утверждение.
  • , Если Ваш метод не принимает, пустые параметрические усилители говорят это в javadoc и используют утверждение.

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

существует предложение добавить новые аннотации в Java7 для помощи с пустым указателем / notnull параметрические усилители: http://tech.puredanger.com/java7/#jsr308

93
ответ дан 2 revs, 2 users 100% 17 April 2018 в 17:15
поделиться
  • 1
    Я должен, вероятно, добавить что, проверив на _value == nullptr doesn' t фиксируют это, но это - другая история. – user3125280 19 January 2014 в 02:25

Вместо Шаблона Несуществующего объекта - который имеет его использование - Вы могли бы рассмотреть ситуации, где несуществующий объект является ошибкой.

, Когда исключение будет выдано, исследуйте отслеживание стека и работу через ошибку.

72
ответ дан Jim Nelson 17 April 2018 в 17:15
поделиться
  • 1
    @treap, осторожный относительно общих мест. Не легко предположить, будет ли разворачивание прибыльным, это иногда isn' t (иначе компиляторы просто шли бы вперед и всегда делали бы это). Таким образом, если Вы не нашли определенное место, где компилятор не разворачивал, но Вы, оказывается, знаете, что разворачивание включило бы большие упрощения (как здесь, куда мы можем удалить код полностью), избегайте преждевременной оптимизации. – Marc Glisse 22 January 2014 в 15:04

Иногда, у Вас есть методы, которые воздействуют на его параметры, которые определяют симметричную операцию:

a.f(b); <-> b.f(a);

, Если Вы знаете, b никогда не может быть пустым, можно просто подкачать его. Это является самым полезным для, равняется: Вместо foo.equals("bar"); лучше делают "bar".equals(foo);.

73
ответ дан 4 revs, 4 users 50% 17 April 2018 в 17:15
поделиться
  • 1
    @treap, который различие - то, что для массива, Вы получаете цикл (который gcc не удается развернуть), в то время как с парами Вы получаете плоскую версию непосредственно. – Marc Glisse 20 January 2014 в 22:33

В зависимости от каких объектов Вы проверяете, что можно быть в состоянии использовать некоторые классы в апачском свободном городском населении, таком как: апачское свободное городское население Ленг и апачские наборы свободного городского населения

Пример:

String foo;
...
if( StringUtils.isBlank( foo ) ) {
   ///do something
}

или (в зависимости от того, что необходимо проверить):

String foo;
...
if( StringUtils.isEmpty( foo ) ) {
   ///do something
}

класс StringUtils является только одним из многих; существует довольно много хороших классов в свободном городском населении, которое действительно аннулирует безопасное управление.

Здесь следует примеру того, как можно использовать пустую проверку в JAVA при включении апачской библиотеки (commons-lang-2.4.jar)

public DOCUMENT read(String xml, ValidationEventHandler validationEventHandler) {
    Validate.notNull(validationEventHandler,"ValidationHandler not Injected");
    return read(new StringReader(xml), true, validationEventHandler);
}

И если Вы используете Spring, Spring также имеет ту же функциональность в своем пакете, посмотрите библиотеку (пружина-2.4.6.jar)

Пример о том, как использовать этот статический classf с пружины (org.springframework.util. Утверждайте)

Assert.notNull(validationEventHandler,"ValidationHandler not Injected");
121
ответ дан 3 revs, 3 users 68% 17 April 2018 в 17:15
поделиться

Я попробовал NullObjectPattern, но для меня не всегда лучший способ пойти. Существуют иногда, когда "никакое действие" не является appropiate.

NullPointerException Исключение на этапе выполнения , который означает, что это - отказ разработчиков, и с достаточным опытом это говорит Вам точно, где ошибка.

Теперь к ответу:

Попытка сделать все Ваши атрибуты и ее средства доступа максимально частными или постараться не представлять их клиентам вообще. У Вас могут быть значения аргументов в конструкторе, конечно, но путем сокращения объема Вы не позволяете клиентскому классу передать недопустимое значение. Если необходимо изменить значения, можно всегда создавать новое object. Вы проверяете значения в конструктора [только 1 110] однажды и в остальную часть методов, можно быть почти уверены, что значения не являются пустыми.

, Конечно, опыт является лучшим способом понять и применить это предложение.

Байт!

19
ответ дан 3 revs, 2 users 91% 17 April 2018 в 17:15
поделиться

Выяснение, чтобы вопрос указал, что можно интересоваться стратегиями обработки ошибок. Архитектор Вашей команды должен решить, как работать ошибки. Существует несколько способов сделать это:

  1. позволяют Исключениям слегка колебаться через - ловят их в 'основном цикле' или в некоторой другой руководящей стандартной программе.

    • проверка на состояния ошибки и обрабатывает их соответственно

Уверенный, действительно взглянули на Аспектно-ориентированное программирование, также - у них есть аккуратные способы вставить if( o == null ) handleNull() в Ваш байт-код.

33
ответ дан xtofl 17 April 2018 в 17:15
поделиться

Платформа наборов Google предлагает хороший и изящный способ достигнуть пустой проверки.

существует метод в классе библиотеки как это:

static <T> T checkNotNull(T e) {
   if (e == null) {
      throw new NullPointerException();
   }
   return e;
}

И использование (с import static):

...
void foo(int a, Person p) {
   if (checkNotNull(p).getAge() > a) {
      ...
   }
   else {
      ...
   }
}
...

Или в Вашем примере:

checkNotNull(someobject).doCalc();
75
ответ дан 3 revs, 3 users 83% 18 April 2018 в 03:15
поделиться
  • 1
    @cmaster я зафиксировал свой ответ для решения этой проблемы (никакая предназначенная игра слов) – user3125280 19 January 2014 в 21:36

В конечном счете, единственный способ полностью решить эту проблему - использовать другой язык программирования:

  • В Objective-C вы можете выполнить эквивалент вызова метода на nil , и абсолютно ничего не произойдет. Это делает ненужными большинство нулевых проверок, но может значительно затруднить диагностику ошибок.
  • В Nice , языке, производном от Java, есть две версии всех типов: потенциально-нулевая версия и непустая версия. Вы можете вызывать методы только для ненулевых типов. Типы с потенциально нулевым значением можно преобразовать в типы, отличные от NULL, путем явной проверки на значение NULL. Это значительно упрощает определение того, где необходимы нулевые проверки, а где нет.
51
ответ дан 17 December 2019 в 16:00
поделиться

, Если неопределенные значения не разрешены:

Вы могли бы настроить свой IDE для предупреждения вас о потенциальном пустом разыменовании. Например, в Eclipse, см. Предпочтения> Java> Компилятор> Ошибочное/Предупреждение/Пустой указатель анализ .

, Если неопределенные значения разрешены:

, Если вы хотите определить новый API, где неопределенные значения имеют смысл , используйте Образец Опции (может быть знакомым с функциональных языков). Это имеет следующие преимущества:

  • указано явно в API, существует ли ввод или вывод или нет.
  • компилятор вынуждает вас обработать "неопределенный" чехол.
  • Опция является монадой , таким образом, нет никакой потребности в подробной пустой проверке, просто используйте map/foreach/getOrElse или подобный combinator для безопасного использования значения (пример) .

Java 8 имеет встроенное Дополнительный (рекомендуемый) класс; для более ранних версий существуют альтернативы библиотеки, например Гуава Дополнительные или опция FunctionalJava . Но как много узоров функционального стиля, с помощью Опции в Java (даже 8) приводит к некоторому шаблону, который можно уменьшить использование менее подробного языка JVM, например, Scala или Xtend.

, Если необходимо иметь дело с API, который мог бы возвратиться, аннулирует , вы не можете сделать многого в Java. Xtend и Groovy имеют оператор Elvis?: и пустой безопасный разыменовывают оператор ?. , но примечание, что это возвращает пустой указатель в случае нулевой ссылки, таким образом, это просто "задерживает" правильное обращение пустого указателя.

191
ответ дан 17 December 2019 в 16:00
поделиться

Если вы используете (или планируете использовать) Java IDE, например JetBrains IntelliJ IDEA , Eclipse или Netbeans или такой инструмент, как findbugs, тогда вы можете использовать аннотации для решения этой проблемы.

По сути, у вас есть @Nullable и @NotNull .

Вы можете использовать в методе и параметрах, например:

@NotNull public static String helloWorld() {
    return "Hello World";
}

или

@Nullable public static String helloWorld() {
    return "Hello World";
}

Второй пример не компилируется (в IntelliJ IDEA).

Когда вы используете первую функцию helloWorld () в другом фрагменте кода:

public static void main(String[] args)
{
    String result = helloWorld();
    if(result != null) {
        System.out.println(result);
    }
}

Теперь компилятор IntelliJ IDEA сообщит вам, что проверка бесполезна, поскольку helloWorld () функция никогда не вернет null .

Использование параметра

void someMethod(@NotNull someParameter) { }

, если вы напишете что-то вроде:

someMethod(null);

Это не будет компилироваться.

Последний пример с использованием @Nullable

@Nullable iWantToDestroyEverything() { return null; }

Выполнение этого

iWantToDestroyEverything().something();

И вы можете быть уверены, что этого не произойдет. :)

Это хороший способ позволить компилятору проверить что-то большее, чем обычно, и заставить ваши контракты быть сильнее. К сожалению, это поддерживается не всеми компиляторами.

В IntelliJ IDEA 10.5 и более поздних версиях они добавили поддержку любых других @Nullable @NotNull реализаций.

См. Сообщение в блоге Более гибкие и настраиваемые аннотации @ Nullable / @ NotNull .

604
ответ дан 17 December 2019 в 16:00
поделиться

В дополнение к использованию assert вы можете использовать следующее:

if (someobject == null) {
    // Handle null here then move on.
}

Это немного лучше, чем:

if (someobject != null) {
    .....
    .....



    .....
}
34
ответ дан 17 December 2019 в 16:00
поделиться

Для служебных классов можно проверить, что параметры не имеют значения null.

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

0
ответ дан 17 December 2019 в 16:00
поделиться
Другие вопросы по тегам:

Похожие вопросы: