что является более производительным равным или instanceof? - PullRequest
0 голосов
/ 22 мая 2019

Какой метод используется исполнителем?

равно:

public boolean hasSellByDate(Object item) {
  if ("Pear".equals(item.getClass().getSimpleName())) {
    return true;
  }
  return false;
}

instanceof:

public boolean hasSellByDate(Object item) {
   if (item instanceof food.Pear) {
     return true;
   }
   return false;
 }

Какие различия имеют эти два метода и какие у них есть недостаткив каждом конкретном случае?

Ответы [ 2 ]

3 голосов
/ 22 мая 2019

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

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

Что касается производительности, вам нужно будет выполнить тестирование, но я ожидаю, что второй также будет быстрее, поскольку instanceof - это единственный код операции на JVM (https://en.wikipedia.org/wiki/Java_bytecode_instruction_listings).

1 голос
/ 22 мая 2019

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

Обратите внимание, что все четыре варианта функционально различны!

# 1

public boolean hasSellByDate(Object item) {
  if ("Pear".equals(item.getClass().getSimpleName())) {
    return true;
  }
  return false;
}

# 2

public boolean hasSellByDate(Object item) {
  if (item instanceof food.Pear) {
    return true;
  }
  return false;
}

# 3

public boolean hasSellByDate(Object item) {
  if ("food.Pear".equals(item.getClass().getName())) {
    return true;
  }
  return false;
}   

# 4

public boolean hasSellByDate(Object item) {
  if (item.class == food.Pear) {
    return true;
  }
  return false;
}

Производительность (по крайней мере, в OpenJDK HotSpot JVM):

  • #4 является самым быстрым
  • #2 и #3 будет близко, #2, вероятно, будет самым быстрым после раундаJIT-компиляция
  • #1 может быть реальным узким местом производительности, особенно в многопоточной среде

Class.getSimpleName() может быть неоправданно медленной из-за глобальной критической секции и манипуляции со строками.Я видел, что когда-то это было реальным узким местом производительности.Метод использовался для форматирования сообщений журнала.

По стилю я бы рекомендовал #2 и #4 в зависимости от функциональных потребностей.

И еще раз подчеркну, все четыре вариантафункционально разные!

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