Программист про (преждевременную) оптимизацию
Всем привет, работаю java разработчиком больше 10 лет. У написанного кода есть разные характеристики: производительность, читаемость, покрытие тестами, стоимость строки итд. Команды разработки могут управлять этими характеристиками в некоторых пределах. В этом посте хотел бы осветить вопрос оптимизации производительности.
Как мыть руки перед едой, программисту не приходится задумываться над небольшими оптимизациями, которые хорошо ложатся на модель данных, при этом имеют меньшую алгоритмическую сложность. Например, посетителей страницы соцсети представлять как множество, а не как список, потому что поиск по множеству происходит быстрее:
List<String> visitorIds;
Set<String> visitorIds;
print(visitorIds.contains("123"));
Иногда требуется подготовить данные, переложить их один раз, чтобы дальнейший поиск происходил быстрее - не сложный со стороны модели код, но требующий внимательности.
Сложнее обстоит дело с индексами в БД - есть инструменты чтобы выбрать правильные индексы, но этот вопрос нужно решать на месте. Не добавил индекс - будет медленное чтение, добавил индекс - медленная запись и повышенное потребление диска. Потребовалось добавить индекс на большом размере данных - нужно останавливать сервис.
Еще сложнее обстоит вопрос с настройкой ресурсов - какой размер пула потоков установить? Кто съел все коннекты к бд, почему повышенное потребление памяти? На этом этапе приходится подключать средства профилирования. Для получения воспроизводимого результата нужно иметь процедуру нагрузочного тестирования. Как будем мерять производительность - по пропускному потоку или по задержке?
Оптимизация производительности обычно бьет по читаемости кода, ведет к усложнению эксплуатации и внесении доработок. Идти на этот компромисс нужно, когда взвешены плюсы и минусы технического решения. В случае производительности - это фактические или предсказанные боттлнеки.
Начинающие разработчики зачастую пытаются необоснованно улучшать производительность за счёт других параметров, этот подход называется преждевременной оптимизацией. При этом они упускают из виду фактическую необходимость изменений, не понимают как будут измерять результат. Примеры таких решений:
перенести всю логику из java в sql (код админки, нагрузка ~100 запросов в день)
ускорить расчет закрытия предыдущего дня (при том что расчет не нуждался в ускорении)
использовать параллелизацию (что ломает компоненты, ориентированные на thread per request подход)
Общая рекомендация здесь такая - если вы не знаете, что делаете - лучше не делать ничего. Сделайте по-простому, и потом улучшайте там где вылезают самые острые проблемы. Желаю всем интересных задач и достойной оплаты!
Временные кэши - не слышали? В целом это тоже можно решить средствами SQL, вопрос надо ли нужно расмматривать в контексте конкретной задачи, а не абстрактных рассуждений, скидывание оптимизации на SQL не всегда плохо, базы умеют работать довольно шустро с большими выборками, а если вы умеете писать на SQL запросы больше чем Select Where то и проблем у вас не возникнет скорее всего.
Для этого нужно не заниматься рассказом про то как вы кота своего гладили на очередном дейлике, а серьезным проектированием, в идеале с техлидами и архитектором, а также аналитиками и проджект менеджерами представляющими развитие проекта на перспективу как минимум года вперед.
К тому же никто не мешает вам создавать мини таблицы с temp выборками на лету, времянки неплохой вариант, а таблицы надо делать так чтобы у вас было как можно меньше миллионников которые эффективно работают лишь с хэш выборками.
Возникает вопрос - почему вы изначально приняли некорректное архитектурное решение(это не разработка нифига, это архитектура)? И причем тут разработчик начинающий, он что ли решение принимал?
Опять нет контекста, что именно вы оптимизируете?
Я анализировал планы запросов, но я никогда не доходил до профайлера.
Размер пула потоков? - ах да это же офигенная джава...
Кто съел все коннекты - а че у вас ваши тесты не заметили что у вас нет завершения соединений?
Это вообще не особо-то дело для разрабов, то о чем вы говорите дело тестировщиков.
Каких других? Вы и первые то параметры не назвали...
Это невозможно объективно. В конце концов вы принимаете решение исходя из догадок о том каким должен бы получится продукт, времени, сил и доступа к ресурсам с требованиями.
Конкретики у вас на руках обычно нет, так что это не компромисс, это подход экономии на спичках там где нет требования, нужно учить читать требования в том числе, а с опытом придет понимание что энтерпрайз переписывается буквально постоянно из-за всякой хрени.
Не ломает, если вы правильно эти компоненты сделали и ее использовали, вообще очень разумная вещь, насмотрелся я на легаси малопоточки.