Есть ли способ сделать совокупные функции в Google App Engine?
Одной из хороших возможностей поддержки реляционных баз данных являются агрегированные функции, такие как count, sum, avg и т.д. Но кажется, что если вы используете GAE, при вставке или обновлении записи вы должны вычислять и хранить счет, сумму, avg и т.д. значения всей таблицы. Но что, если у вас много условных группировок? Учитывая человека:
class Person {
@Id
Integer age;
String city;
}
Если я хочу
- общее число лиц
и
- средний возраст
Правильно ли, что каждый раз, когда я создаю, обновляю или удаляю человека, я должен также вычислять оба агрегата и хранить их как отдельные столбцы в одной таблице. Если мне также нужны общие и средние значения для каждого города, следует ли хранить эти значения для каждого города также как отдельные столбцы в одной таблице?
Ответы
Ответ 1
Правильно: для правильного использования хранилища GAE вам необходимо выборочно де-нормализовать некоторые аспекты вашей модели, сохраняя "избыточные" данные, которые в DB в нормальной форме вы перекомпонуете "на лету", например, агрегаты ( общий и "сгруппированный по" ).
Однако не добавляйте такие поля в таблицу Person
в вашем случае - это мало смысла! Создайте еще одну таблицу PersonAggregates
с такими столбцами, как City (null/missing для общих итогов), Count, TotalAges (проще в обслуживании: вычислить среднее значение в любое время как общее количество по счету).
Ответ 2
Для часто используемых агрегатов лучше всего обновлять их при каждом обновлении/вставке/удалении.
Если вы не создали такие агрегаты в своем приложении с самого начала, вы можете запустить script через Remote DataStore API или настроить серверную
задание cron, которое будет обрабатывать все сущности и вычислять агрегаты. Это довольно просто, просто помните о квоте процессора для каждого запроса.