Optimizing Insert in PostgreSQL: index locality

There are tons of materials around there on how to optimize selects, how plans work and so, but almost no information on how to optimize insert/update/delete operations. At least I haven’t found what I needed so I wish to tell my story.

First of all a bit of environment: I have a large part of database for search (well it counts in tens of millions of records) with need for
a) fast search (so there must be some indexes).
b) fast update with lots of data (again several millions of records of updates a day are usual).
c) some sort of uniqueness so that cache contains only latest record for some condition.

Actually insert/update/delete optimization is pretty simple: every index you have slows updates down, so don’t make too much of them. But there is another case to consider: how much pages of index would be updated in case of data update.

In my situation the goal c) was achieved by using md5(of some fields), this is quite a good key it has perfect distribution (there are no repeating numbers and also they are spred very well). It’s also quite usefull in operations: single field in index, single equality in join.

But there was one problem: when I tried to insert let’s say 100K rows with new equality keys it distributed almost to every page of an index, so operation was very sloowww. Thanks to good distribution of equality_key :) . Sadly situation get only worse over time as overall size grows, because updates are still very random.

Solution in my case was to «group» this index in a manner it is updated (in my case it is hotel_id, departure_date, and only then equality_key). This gives much better locality in updates and little impact in search perfomance (actually due to locality impcat should be even positive). I have some numbers but they wouldn’t say much and it’s not a purpose of this post. In my case update perfomance was boosted by an order of magnitude, and it should degrade so much with growth of DB size, so now I’m happy :) .

The overall rule to consider in optimizing inserts/updates/deletes is to look on how many index pages would be updated in typical update situation (i.e. index could be thought as table records sorted in index order (actually it’s a lot different, but still model is very nice in many situations)). Ideally only pages, related to new data should be updated almost fully, and other should not be touched.

This might be very very simple and obvious when you know about it. But some people (like me) don’t know this. I hope this would help.


Получение пути к свойству, несколько мыслей, QueryDSL

Наткнулся тут на http://blog.mysema.com/2010/07/querying-hibernate-with-querydsl.html – по своему интересная игрушка . Тут описан вариант с кодогенерацией через процессор анотаций, но в доках есть вариант и без него, примерно так: Cat c = alias(Cat.class, "cat"); List<String> names = from($(c),cats)   .where($(c.getKittens()).size().gt(0))   .list($(c.getName()));   for (String name : names){     System.out.println(name); } Порывшись в исходниках нашёл


Проблема редактирования и состояния объектов

Как работает абстрактный редактор в GUI? Очень просто – ему даётся некоторый объект, он его хавает, заполняет по нему то, что должен сейчас редактировать, дальше ОК/Отмена, если ОК – проверяет, всё ли правильно введено и если всё верно – применяет редактирование к объекту. И тут всё просто и хорошо. А вот что, если отмена? По


Пустячок с LEFT JOIN или NULL != NULL is false и NULL = NULL is false

Довольно таки интересная штука, помоему в жизни каждый программист на неё пару раз напоролся. Если не помнит, значит ему повезло.. я в своё время хорошо налетел на часик отладки. Простой запрос: SELECT o.*, m.* FROM   orders o   LEFT JOIN manager m ON m.id = o.manager_id WHERE   m.is_active = true Запрос простой, тут


Область видимости переменных

Думал с чего начать, это показалось самым простым. Собственно речь о том, где и как хранить и передавать информацию между частями программы. Самое простое в программе – локальные переменные. Почему? Они живут на стэке => существует один экземпляр для одного вызова функции. Вся работа с ними у нас перед глазами – все изменения и чтения


Мы ограниченные, и это нормально

Программист – существо ограниченное, я например – точно: Я не могу держать в голове более 7 +/- 2 вещей. У меня хорошая память, но я не могу запомнить все переменные, выражения, методы и классы в программе. Также я не могу помнить все зависимости в коде. Я плохо читаю запутанный код (и не хочу этого делать).


Разработка

Давно я не писал. Не знаю, получится ли цикл заметок, как хотелось бы, или нет, но что-то хотелось бы. Цель – всё та же, структурировать текущую картину мира, для себя – чтобы в очередной раз всё вспомнить и для других, чтобы этим поделиться. Заметка первая, зачем всё это нужно. Мы никогда ничего не пишем только


ОО программирование, как я его сейчас понимаю

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


Отпуск (Крым, май 2009)

В двух словах, как это было – было здорово. Мы сходили в поход в районе Демерджи. С погодой повезло не особенно – первую часть путешествия был мелкий дождик (а стоянка в районе агнарского перевала так и вообще проходила в облаке – тот же мелкий дождь + сильный туман). Потом всё более-менее раздуло и облачка чередовались


Пара идей по отладке

Очень много раз порывался написать такую заметку и как-то каждый раз или не выходило, или выходило криво, так, что не нравилось. Сейчас есть настроение, попробую снова. На самом деле, я наверное больше хочу сделать акцент на теории, нежели чем на практике, дать несколько советов, а по практике – опыт ничто не заменит. Что такое отладка?