Каков наилучший способ представления расписания в базе данных через Python / Django? - PullRequest
0 голосов
/ 06 марта 2009

Я пишу систему резервного копирования на Python с интерфейсом Django. Я решил реализовать планирование немного странным образом - клиент будет опрашивать сервер (каждые 10 минут или около того), чтобы получить список резервных копий, которые необходимо выполнить. Сервер будет отвечать только по истечении времени резервного копирования. Это сделано для того, чтобы сохранить системную платформу независимой - чтобы я не использовал cronjobs или что-то подобное. Поэтому клиентский интерфейс Django (который предоставляет API-интерфейс XML-RPC) должен хранить расписание в базе данных и интерпретировать это расписание, чтобы решить, следует ли клиенту начать резервное копирование.

В настоящее время расписание хранится в 3 полях: дни, часы и минуты. Это разделенные запятыми списки целых чисел, представляющие дни недели (0-6), часы дня (0-23) и минуты часа (0-59). Чтобы решить, должен ли клиент начать резервное копирование или нет, это ужасно неэффективная операция - Python должен циклически повторять все дни, прошедшие 7 дней в прошлом, затем часы, затем минуты. Я провел некоторую оптимизацию, чтобы убедиться, что она не зацикливается - но все же!

Это работает относительно хорошо, хотя реализация довольно уродливая. Проблема у меня заключается в том, как отобразить и интерпретировать эту информацию через форму HTML на внешнем интерфейсе. В настоящее время у меня просто огромные списки полей с несколькими вариантами выбора, что, очевидно, не очень хорошо работает.

Может ли кто-нибудь предложить другой метод реализации расписания, который был бы более эффективным, а также более простым для представления в форме HTML?

Ответы [ 2 ]

3 голосов
/ 06 марта 2009

Взгляните на Джанго-хронограф . Он имеет довольно приятный интерфейс для планирования заданий на все виды интервалов. Возможно, вы сможете позаимствовать некоторые идеи из этого. Он опирается на python-dateutil , что также может оказаться полезным для указания повторяющихся событий.

0 голосов
/ 17 мая 2016

Ваш вопрос немного двусмысленный - вы имеете в виду: "Резервировать каждое воскресенье, понедельник и пятницу во время X". ?

Если это так, используйте Битовая маска для сохранения повторяющегося расписания в виде целого числа:

Допустим, вам нужна резервная копия, как указано выше - по воскресеньям, понедельникам и пятницам. Кодируйте дни недели целым числом (представлено в двоичном формате):

S M T W T F S
1 1 0 0 0 1 0 = 98

Чтобы выяснить, является ли сегодня (например, пятница) резервным днем, просто сделайте побитовый and:

>>> 0b1100010 & 0b0000010 != 0
True

Чтобы получить текущий день в виде целого числа, его необходимо сместить на единицу, поскольку weekday() предполагает, что неделя начинается в понедельник:

current_day = (timezone.now().weekday() + 1) % 7

В итоге схема для вашего Schedule объекта будет выглядеть примерно так:

class Schedule(models.Model):
    days_recurrence = models.PositiveSmallIntegerField(db_index=True)
    time = models.TimeField()

При использовании этой схемы вам потребуется новый объект Schedule для каждого времени дня, в которое вы хотите выполнить резервное копирование. Это быстрый поиск, так как побитовая операция стоит около 2 циклов, и, так как вы индексируете поле days_recurrence, у вас есть дневной поиск в худшем случае O(logn), который должен значительно сократить вашу сложность. Если вы хотите повысить производительность, вы также можете использовать битовую маску для час , а затем сохранить минуты.

...