Доброго времени суток, дорогой читатель!
Ниже небольшой набор тестов, показывающих статистику по вставке/чтению в/из таблицы/коллекции. Понятно, что никакой тест не покажет реальной картины, которая будет происходить в вашем приложении. Но всё-таки из чистого любопытства я решил провести некоторые замеры. Результаты и выводы к которым я пришёл под катом.
На чём тестировалось:
Название ОС: Windows 7 Professional
Архитектура ОС: AMD64
Имя процессора: Intel® Core(TM) i5-3340 CPU @ 3.10GHz
Производитель: GenuineIntel
Архитектура процессора: AMD64/EM64T
Физических ядер: 2
Логических процессоров: 2
Всего оперативной памяти: 8139 MB (7.95 GB)
Для mongo использовалась последняя врсия официального драйвера
Для mc использовал тот, который потянул нагрузку. Использовал с 10 разных клиентов, какие-то просто не завелись, какие-то пытались работать асинхронно и падали.
Версия mongo: 2.6.3
Версия mc: 1.4.4-14-g9c660c0 (последняя из тех, что удалось найти скомпиленным для винды)
Версия erlang: 5.10.4/OTP R16B03
Небольшая ремарка перед началом.
Предвижу вопрос, вида: «А при чём здесь mongo, как можно сравнивать хранилище в памяти с хранилищем на диске?!». Вопрос резонный. Ответ простой: мне стало интересно. И поэтому я сделал сравнение тех хранилищ, которые популярны и для которых есть драйверы в Erlang.
Напоминаю, все тесты, можно отнести к разряду сферических в вакууме.
Итак приступим.
Вставка
Первое, что я решил проверить это скорость вставки записей и потребляемую на это память, результат был ожидаем:
Native Ets-таблицы дали фору всем остальным опередив ближайшего конкурента, dets, более чем в 10 раз. Но впрочем это и логично, так как ets работает в памяти а dets на диске. Mc тоже работает в памяти, но, видимо. из-за драйвера (погуглив нашёл результаты примерно вдвое большей скорости работы), отстал почти в 70 раз, монга оказалась немного быстрее.
При выполнении операции вставки 10кк записей Mongod употребил 2,7 Гб оперативной памяти, на ets ушло 2,87 Гб, а Mc понадобилось 1,6.
Выборка:
Здесь откровения тоже не произошло. Ets оказались самыми быстрыми, следом за ними идут dets, потом Mc и следом mongo, но тут следует посмотреть на последний результат. При работе с большим количеством записей Dets становится не эффективен, причём чем больше число записей, тем ниже эффективность, здесь Mc его обходит. Для mongo был сделан индекс по полю выборки.
Ну и напоследок, количество записей, который могут быть обработаны за одну секунду:
Чуть-чуть выводов
Минутка кэпа: для кэширования данных нужно использовать встроенные средства.
И, казалось бы, действительно, что мешает использовать ets-таблицы? Благо хранить в них можно любые термы. Основной минус, данные хранятся в памяти, и если процесс, создавший таблицу, упадёт, то таблица исчезнет вместе с ним, утянув за собой процессы которые к ней в этот момент обращаются. Да, процесс будет перезапущен супервизором, но данные то все, тю-тю. Ок, давайте использовать dets, тут все храниться на диске и ничего не потеряется. Да, но, ох уж это «но», время повторного открытия и проверки таблицы на повреждения при большом размере файла весьма существенно, ваши процессы врят ли будут ждать. Так что же остаётся Mc, который, кстати, тоже может упасть по какой-нибудь причине, или Monga, или, или…
Да, суровая реальность такова, что всё может упасть, но, допустим у Mc или Mongo есть возможность разворачивать кластеры, и если падает одна машина, всегда можно обратиться к другой. Но они самые медленные из протестированных систем. Вот и приходится выбирать, чем жертвовать, либо производительностью, либо данными.
Хотя можно и не выбирать и не жертвовать, для себя я пришёл к следующим выводам:
1) В ets нужно хранить «горячий» кэш данных, который постоянно требуется и потеря которого не сулит больших проблем. А еще документация нам подсказывает, что dets таблицы можно открыть и использовать в памяти, а при закрытии они дампятся на диск. Но, как видно из тестов, dets эффективны при небольшом размере данных, иначе время работы с диском становится слишком большим.
2) Все данные, которые для вас критичны, нужно сохранять в надёжное хранилище, не важно, sql/nosql куда-то, где вы будете за них спокойны.
3) Нужен модуль, аналогичный Mc, но на ets таблицах, который позволит необходимые данные записывать в «горячий» кэш, чтобы они были сразу доступны, и в синхронном/асинхронном режиме сможет переносить их в другие хранилища
Выводы получились капитанскими, но, наверное, все выводы из каких-то замеров примерно одинаковы и где-то, когда-то, уже звучали.
Благодарю за внимание.
Автор: Slavenin999