2009-01-09 49 views
6

我需要存儲一次,每天,每週,每週,每週的某幾天,每月的某幾天可能是數字還是符號,比如每個月的第一個星期一,等等。您將如何存儲可能的經常性時間?

有什麼建議嗎?任何代碼,數據結構或模式來看?

回答

1

這聽起來像 「復發事件」,如在Outlook中。我會使用一個名爲RecurrenceType的表來存儲每個時間段(每天,每週等)。另一個名爲Event woud的表通過RecurrenceType的鍵引用。然後可以使用標準日期函數計算大多數重複類型的未來日期。

8

有複雜的解決方案和簡單的解決方案。最簡單的兩個解決方案:

  1. 扇出重複事件多達某個常數許多情況下,或最多在未來的某個固定日期範圍。存儲FK recurrence_id,每個實例指向重複的描述,並允許批量編輯和取消。

    預定義扇出方法的優點是它可以非常容易地執行重複異常,這幾乎肯定會成爲您獲得的第一個功能請求。

  2. 在顯示時間計算。計算機速度很快,取決於您希望能夠回答您的數據的問題,計算日期範圍內的所有事件通常會非常容易。在進行重複計算之前,您可以很聰明並嘗試快速將日期範圍括起來,或者可以從發病日期開始蠻力。

除此之外,您只需要一個解決方案來存儲重複規則,該規則適用於計算重複出現的任何內容。 (例如,如果您使用的是iCalendar啓用庫,則您的模式爲varchar(255),其中包含RRULE值)

如果您不得不推出自己的重複計算器,並且希望保持簡單,您每天,每週,每月或每年的重現率覆蓋您的第一個80%用例,並且非常容易計算。

此時你的潛在復發的架構看起來像:

id 
recurrence_start 
recurrence_end 
type (daily|weekly|monthly|yearly) 
day_of_week (for weekly) 
month 
day_of_month 

而與此同時,複雜的解決方案可能是不值得的:)

+0

嘿kellan,您將如何使用您提供的重複模式來實現事件的範圍(開始和結束日期)?有任何想法嗎?我在設計這樣的東西時遇到了很多麻煩。謝謝! – Tom 2014-08-12 03:42:17

1

的問題是,有指定這樣的無限可能間隔。例如 - 「每隔一個月的第一個星期一,如果日期是偶數,但不是4,並且這個月不是漫長的一年的二月」。你願意走多遠?最終你只需要讓用戶鍵入一個布爾表達式,在事件重新發生的日子裏,這個布爾表達式的值爲TRUE。從用戶界面角度看,這不太好。

您應該爲您的系統決定一些限制。一旦你知道了這些,其餘的應該很容易 - 或者至少在SO上負責。 :)

3

Martin Fowler對此寫了a really great paper。您可以在runt中找到許多與他討論的相同的想法,這是一個用於處理時態表達式的Ruby庫。

+1

Fowler的論文清晰易讀,但它並不涉及規則的例外情況,IMO是這種設計模式中的一個棘手問題...... – 2009-05-20 11:31:38

0

它提到的a related, useful SO thread,但如果你碰巧使用Ruby是ice_cube一個很好的,積極維護替代小個子。你沒有提到你的存儲後端需求是什麼,但對於數據庫模式,@ kellan和上述線程中的一些是好的開始。

相關問題