Разница в производительности между предложениями lodash "get" и "if else" - PullRequest
1 голос
/ 20 марта 2019

Допустим, у вас есть объект машинописного текста, где любой элемент может быть undefined.Если вы хотите получить доступ к сильно вложенному компоненту, вы должны сделать много сравнений с undefined.

. Я хотел бы сравнить два способа сделать это с точки зрения производительности: обычные if-else сравнения ифункция lodash get.

Я нашел этот прекрасный инструмент под названием jsben , где вы можете тестировать различные части кода js.Однако я не могу правильно интерпретировать результаты.

В этом тесте lodash get кажется немного быстрее.Однако, , если я определю свою переменную в Setup block (в отличие от Boilerplate code), код if-else будет быстрее с большим отрывом.

Что является правильнымспособ сравнительного анализа всего этого?Как я должен интерпретировать результаты?get настолько медленнее, что вы можете аргументировать в пользу предложений if-else, несмотря на очень плохую читаемость?

Ответы [ 2 ]

2 голосов
/ 20 марта 2019

Я думаю, вы задаете не тот вопрос.

Прежде всего, если вы собираетесь проводить микрооптимизацию производительности (в противоположность, скажем, алгоритмической оптимизации), вы должны действительно знать, является ли рассматриваемый код узким местом в вашей системе. Устраняйте наихудшие узкие места, пока ваша производительность не будет в порядке, а затем перестаньте беспокоиться об этом. Я был бы очень удивлен, если бы разница между ними когда-либо превышала ошибку округления в серьезном приложении. Но я был удивлен раньше; отсюда и необходимость проверить .

Затем, когда дело доходит до фактической оптимизации, обе реализации лишь незначительно отличаются по скорости в любой конфигурации. Но если вы хотите проверить глубокий доступ к вашему объекту, похоже, что второй - правильный способ думать об этом. Не похоже, что это должно иметь большое значение в относительных скоростях, но первый помещает код инициализации, где он будет «выполняться перед каждым блоком и является частью теста». Второй помещает его туда, где «он будет запускаться перед каждым тестом и не является частью теста». Поскольку вы хотите сравнить доступ к данным, а не инициализацию данных, это представляется более подходящим.

Учитывая это, кажется, что у техники families && families.Trump && families.Trump.members && ... есть небольшое преимущество в производительности. (Примечание: здесь не видно if с или else с!)

Но стоит ли это того? Я бы сказал нет. Код намного, намного ужаснее. Я бы не стал добавлять библиотеку, такую ​​как lodash (или мою любимую Ramda ), просто чтобы использовать такую ​​простую функцию, как эта, но если бы я уже использовал lodash, я бы не колебался использовать здесь более простой код , И я мог бы импортировать один из lodash или Ramda, или просто написать свой собственный в противном случае, так как это довольно простой код.

Этот нативный код будет быстрее, чем более общий библиотечный код, не должно быть сюрпризом. Это не всегда происходит, так как иногда библиотеки используют ярлыки, которые не может использовать нативный движок, но, скорее всего, это норма. Причина использования этих библиотек редко связана с производительностью, но с написанием более выразительного кода. Здесь выигрывает версия lodash, с рук в руки.

1 голос
/ 20 марта 2019

Как правильно все это оценивать?

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

Как мне следует интерпретировать результаты?

1) проверить, действительны ли они:

Результаты соответствуют вашим ожиданиям? Если нет, может ли быть причина для этого? Копирует ли тестовый пример ваш фактический вариант использования?

2) проверить, соответствует ли результат:

Какое время занимает сравнение с фактическим временем в вашем сценарии использования? Если для загрузки вашего кода требуется 200 мс, а оба теста выполняются менее чем за 1 мс, ваш результат не имеет значения. Однако если вы попытаетесь оптимизировать код, который выполняется 60 раз в секунду, 1 мс - это уже много.

3) проверить, стоит ли результат работы

Зачастую вам приходится много заниматься рефакторингом, или вам приходится много печатать, выигрывает ли прирост производительности за время, которое вы вкладываете?

Является ли get настолько медленнее, что вы можете аргументировать в пользу предложений if-else, несмотря на очень плохую читаемость?

Я бы сказал нет. используйте _.get (если вы не планируете запускать это несколько сотен раз в секунду).

...