2013-02-07 22 views
11

यदि आप कल्पना कर सकते हैं तो यह मेरे सॉफ़्टवेयर में वाई 2 के-स्टाइल बग का कारण बनता है। अजीब बात यह है कि साल-दर-साल की गणना केवल वर्ष में दो दिनों के लिए होती है, जो मुझे कम यकीन है कि समस्या निवारण कैसे करें।जावा दिनांक वर्ष गणना दो दिन के लिए बंद है

उत्पादन:

03-Jan-2013 
02-Jan-2013 
01-Jan-2013 
31-Dec-2013 ** strange 
30-Dec-2013 ** strange 
29-Dec-2012 
28-Dec-2012 
27-Dec-2012 
26-Dec-2012 
25-Dec-2012 

मुझे यकीन है कि जो जावा तारीख उपयोगिताओं का हिस्सा इस तरह के एक त्रुटि का कारण बन सकता नहीं हूँ।

कोड (के बाद से परीक्षण इतना छोटा मैं एक पूरा काम कर कार्यक्रम शामिल है):

import java.util.Calendar; 
import java.util.Date; 
import java.text.SimpleDateFormat; 

public class DateT { 

     private static String getFormattedBackscanStartTime(int days) { 

       SimpleDateFormat dateFormat = new SimpleDateFormat("dd-MMM-YYYY"); 
       Calendar workingDate = Calendar.getInstance(); 
       workingDate.add(Calendar.DATE, -1 * days); 

       String formattedStartTime = dateFormat.format(workingDate.getTime()); 
       return formattedStartTime; 
     } 

     public static void main(String args[]) { 

       for(int i = 35; i < 45; i++) { 
         System.out.println(getFormattedBackscanStartTime(i)); 
       } 
     } 
} 
+0

मुझे लगता है कि आपको इससे फायदा होगा। https://forums.oracle.com/forums/thread.jspa?threadID=2096000 – Achrome

+2

ध्यान रखें कि 'कैलेंडर' और 'SimpleDateFormat' कक्षाएं अब [विरासत] हैं (https://en.wikipedia.org/wiki/ विरासत प्रणाली)। [Java.time] द्वारा प्रत्याशित (https://docs.oracle.com/javase/8/docs/api/java/time/package-summary.html) कक्षाएं। एक आधुनिक दृष्टिकोण 'लोकलडेट', 'जोनआईडी', और' डेटटाइमफॉर्मेटर 'कक्षाओं का उपयोग करता है। डीबगिंग चरण –

उत्तर

26

यह समस्या है:

"dd-MMM-YYYY" 

YYYY सप्ताह साल, नहीं कैलेंडर है साल। आप इसके बजाय yyyy चाहते हैं।

कैलेंडर वर्ष 2012 के अंतिम दो दिन सप्ताह-वर्ष 2013 के पहले सप्ताह में थे। आपको आमतौर पर सप्ताह के वर्ष का उपयोग "वर्ष का सप्ताह" विनिर्देशक (w) के साथ करना चाहिए।

2

समस्या आपकी दिनांक प्रारूप स्ट्रिंग में निहित है - वर्ष yyyyYYYY नहीं होना चाहिए।

आपको लूप से प्रत्येक चरण में workingDate.getTime() का मूल्य मुद्रित हैं, तो आप यह उम्मीद मान हैं देखेंगे:

Thu Jan 03 11:19:33 EST 2013 
Wed Jan 02 11:19:33 EST 2013 
Tue Jan 01 11:19:33 EST 2013 
Mon Dec 31 11:19:33 EST 2012 
Sun Dec 30 11:19:33 EST 2012 
Sat Dec 29 11:19:33 EST 2012 
Fri Dec 28 11:19:33 EST 2012 
Thu Dec 27 11:19:33 EST 2012 
Wed Dec 26 11:19:33 EST 2012 
Tue Dec 25 11:19:33 EST 2012 

इसलिए समस्या SimpleDateFormat उपयोग में निहित है।

+0

+1 केवल 1.7 को नोट करने के लिए +1। – djechlin

1

आपको वर्ष के लिए कम केस वाई का उपयोग करने की आवश्यकता है। इसे आज़माएं:

SimpleDateFormat dateFormat = new SimpleDateFormat("dd-MMM-yyyy"); 
5

मुझे लगता है कि आप java 1.7 का उपयोग कर रहे हैं।

कोड स्निपेट के ऊपर SimpleDateFormat("dd-MMM-YYYY") रूप java 1.6 साथ काम नहीं करेंगे एक java.lang.IllegalArgumentException बढ़ा देंगे आप yyyy बजाय YYYY उपयोग करने की आवश्यकता है (YYYY java 1.6 में उपलब्ध नहीं है)

Y -> week-year 
y -> year 

here

संपादित

yyyy के साथ महान काम करता है:

$ java DateT 
03-Jan-2013 
02-Jan-2013 
01-Jan-2013 
31-Dec-2012 
30-Dec-2012 
29-Dec-2012 
28-Dec-2012 
27-Dec-2012 
26-Dec-2012 
25-Dec-2012 
+0

+1 के लिए – djechlin

1

पूर्णता के लिए के लिए, यहाँ LocalDate (का उपयोग करते हुए आधुनिक जवाब के रूप में एक टिप्पणी में तुलसी Bourque द्वारा सिफारिश की)।

  • अपने फ़ॉर्मेटर अपने उत्पादन की भाषा के नियंत्रित करने के लिए करने के लिए एक स्पष्ट स्थान दें:

    import java.time.LocalDate; 
    import java.time.format.DateTimeFormatter; 
    import java.util.Locale; 
    
    public class DateT { 
    
        private static DateTimeFormatter dateFormatter 
          = DateTimeFormatter.ofPattern("dd-MMM-uuuu", Locale.US); 
    
        private static String getFormattedBackscanStartTime(int days) { 
         return LocalDate.now(ZoneId.systemDefault()).minusDays(days).format(dateFormatter); 
        } 
    
        public static void main(String args[]) { 
         for(int i = 155; i < 165; i++) { 
          System.out.println(getFormattedBackscanStartTime(i)); 
         } 
        } 
    } 
    

    चल रहा है यह आज मैं

    04-Jan-2017 
    03-Jan-2017 
    02-Jan-2017 
    01-Jan-2017 
    31-Dec-2016 
    30-Dec-2016 
    29-Dec-2016 
    28-Dec-2016 
    27-Dec-2016 
    26-Dec-2016 
    

    कुछ बातें नोट करने के लिए मिला है। भले ही आप Locale.getDefault() पास करें, आप पाठक को बता रहे हैं कि आपने लोकेल के बारे में सोचा है और निर्णय लिया है।

  • इसी प्रकार पाठक को बताने के लिए LocalDate.now() पर एक स्पष्ट समय क्षेत्र दें (उदाहरण के लिए ZoneId.of("America/New_York") एक विशिष्ट समय क्षेत्र के लिए; ZoneId.systemDefault() जेवीएम की वर्तमान समय क्षेत्र सेटिंग के लिए)।
  • मुझे पुराने फैशन Calendar कक्षा का उपयोग कर कोड से कोड सरल और अधिक सरल लगता है। यह नए वर्गों के लिए विशिष्ट है।
  • मैंने वर्ष के लिए uuuu का उपयोग किया है। yyyy (लोअरकेस) भी काम करता है, आम युग (एकेए बीसी) से पहले वर्षों के लिए केवल एक अंतर होगा।
संबंधित मुद्दे