2010-10-20 15 views
10

मैं एक ग्रोवी/जावा कैलेंडर-प्रकार एप्लिकेशन पर काम कर रहा हूं जो उपयोगकर्ता को प्रारंभ तिथि और वैकल्पिक पुनरावृत्ति के साथ ईवेंट दर्ज करने की अनुमति देता है। यदि यह एक आवर्ती घटना है, यह recurr हो सकता है:पुनरावर्ती घटना तर्क

महीने की एक तारीख है कि आरंभ तिथि करने के लिए इस बात का सप्ताह के एक दिन पर
  • साप्ताहिक मेल खाती है पर
    • मासिक आरंभ तिथि से मेल खाती है
    • हर इस बात का सप्ताह के एक दिन पर 2 सप्ताह आरंभ तिथि
    • आदि से मेल खाती है

    मैं मूल रूप से गूगल कैलेंडर एपीआई का उपयोग कर सभी पुनरावृत्ति तर्क करने के लिए योजना बनाई है, लेकिन यह एक बहुत बड़ा PITA साबित हुई , कारणों से अगर कोई परवाह करता है तो मैं आगे चर्चा करूंगा।

    तो अब, मैंने अपना खुद का समाधान रोल करने का निर्णय लिया है। एक तारीख को देखते हुए, मैं यह जानना चाहता हूं कि इस तारीख पर आवर्ती घटना होती है या नहीं। (स्यूडोकोड में) मेरी तर्क इस प्रकार होगी:

    public boolean occursOnDate(def date, def event) { 
    
        def firstDate = event.startDate 
    
        if (firstDate > date) { 
        return false; 
    
        } else if (event.isWeekly()) { 
        return event.dayOfWeek() == date.dayOfWeek() 
    
        } else if (event.isMonthly()) { 
        return event.dayOfMonth() == date.dayOfMonth() 
    
        } else { 
        // At this point we know the event occurs every X weeks where X > 1 
        // Increment firstDate by adding X weeks to it as many times as possible, without 
        // going past date 
        return firstDate == date 
        } 
    } 
    

    यह तर्क उचित लगता है, लेकिन वास्तव में लागू करने के लिए जब आप सभी अजीब किनारे मामलों में (पर विचार काफी प्रयास के एक बहुत हो जाएगा जैसे कि कैसे एक मासिक आवर्ती को संभालने के लिए फरवरी में घटना जिसका पहला घटना 31 जनवरी है)।

    क्या ऐसी कोई पुस्तकालय है जो इसे लागू करने में मेरी सहायता कर सकती है? कुछ विनिर्देशों की बहुत सराहना की जाएगी (उदाहरण के लिए "जोडा समय का उपयोग करें" के लिए कोई क्रेडिट नहीं दिया जाएगा)।

    धन्यवाद, डॉन

  • +0

    इसी प्रकार के प्रश्न: [क्या सबसे अच्छा जावा तारीख पुनरावृत्ति पैटर्न कैलकुलेटर] (http://stackoverflow.com/q/492055/642706) –

    +0

    इस मार्टिन Fowler कागज, [कैलेंडर के लिए घटनाक्रम आवर्ती] (http://martinfowler.com/apsupp/recurring.pdf) उपयोगी हो सकता है। –

    उत्तर

    2

    मैं ग्रूवी बारे में कुछ नहीं पता है, और मेरा पहला सुझाव Joda होने जा रहा था, लेकिन आप इसके बारे में पता है।

    मुझे पता है कि यह आपके लिए अधिक प्रतीत हो सकता है, और शायद लागू भी नहीं हो सकता है, लेकिन Quartz Scheduler यह सभी पुनरावृत्ति और घटनाओं से संबंधित नियमों को बहुत अच्छी तरह से संभालता है। आप अपनी शेड्यूलिंग क्षमताओं का उपयोग नहीं कर सके, और केवल आपके लिए ईवेंट तिथियों की गणना करने के लिए ट्रिगर कक्षाओं (जैसे CronTrigger) का उपयोग करें।

    CronTrigger ऊपर दिए लिंक पर भाव तो आप इस विशेष रूप से बुरा स्थिति की तरह, अपने ईवेंट प्रबंधित करने के इस्तेमाल कर सकते हैं के कुछ उदाहरण दिखाता है: "? 0 0 12 एल *"

    - महीने के हर अंतिम दिन (लीप साल के साथ कोई सिरदर्द नहीं) और 0)

    डेलाइट सेविंग टाइम मुद्दों को भी संभाला जाता है।

    कोड का सवाल है, वांछित पुनरावृत्ति के साथ ट्रिगर बनाने और उसके बाद आप सभी फायरिंग बार आप चाहें निकाल सकते हैं:

    Date firstFireTime = myTrigger.getNextFireTime(); 
    ... 
    while (...) { 
        Date nextFireTime = myTrigger.getFireTimeAfter(previousFireTime); 
        ... 
    } 
    

    आशा इस उपयोगी हो सकता है।

    +0

    यदि आपके पास अपना उद्देश्य प्राप्त करने के लिए जोडा/क्वार्ट्ज का उपयोग कैसे किया जा सकता है, तो मुझे कुछ और विशिष्ट जानकारी है, मुझे यह सुनना अच्छा लगेगा। –

    +0

    ऊपर और जानकारी जोड़ा गया :) – mdrg

    8

    आरएफसी-2445 (मूल रूप से, iCal spec) में उचित पुनरावृत्ति नियमों की तरह उचित रूप से निर्दिष्ट किया गया है। इस सही के minutiae प्राप्त करना काफी शामिल हो सकता है। मैं इसके लिए google-rfc-2445 लाइब्रेरी का उपयोग करने का सुझाव दूंगा, या iCal4J जैसे उस spec का एक और कार्यान्वयन।

    0

    मैं ग्रोवी लाइब्रेरी से बहुत परिचित नहीं हूं लेकिन चूंकि ग्रोवी जेवीएम पर चल रहा है, इसलिए मुझे लगता है कि आप जावा/स्कैला लाइब्रेरी का भी उपयोग करने में सक्षम होना चाहिए।

    आपको जो चाहिए वह एक व्यावसायिक अनुसूची पीढ़ी लाइब्रेरी है जो लामा (http://lamma.io) की तरह सामान्य प्रयोजन दिनांक समय पुस्तकालय जोडा जैसे है।

    // monthly on a date of the month that corresponds to the start date 
        // output: [Date(2014,6,10), Date(2014,7,10), Date(2014,8,10), Date(2014,9,10), Date(2014,10,10)] 
        System.out.println(Dates.from(2014, 6, 10).to(2014, 10, 10).byMonth().build()); 
    
        // weekly on a day of the week of that corresponds to the start date 
        // output: [Date(2014,6,10), Date(2014,6,17), Date(2014,6,24), Date(2014,7,1), Date(2014,7,8)] 
        System.out.println(Dates.from(2014, 6, 10).to(2014, 7, 10).byWeek().build()); 
    
        // every 2 weeks on a day of the week of that corresponds to the start date 
        // output: [Date(2014,6,10), Date(2014,6,24), Date(2014,7,8)] 
        System.out.println(Dates.from(2014, 6, 10).to(2014, 7, 10).byWeeks(2).build()); 
    
        // edge cases are handled properly, for example, leap day 
        // output: [Date(2012,2,29), Date(2013,2,28), Date(2014,2,28), Date(2015,2,28), Date(2016,2,29)] 
        System.out.println(Dates.from(2012, 2, 29).to(2016, 2, 29).byYear().build()); 
    
    संबंधित मुद्दे