Getting wrong month when using SimpleDateFormat.parse
Use:
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Use MM
for month, mm
for minutes as stated by documentation...
If you want to print a Date
in a specific format, you should use:
sdf.format(birthday)
or another SimpleDateFormat
if you want to pring it in a different format...
Java parse date string returns wrong month
This is due to the format you used as "yyyy-MM-DD"
. The parser will parse in the sequence way:
- Your input value is
"2018-03-08"
yyyy
- will bring to the year 2018MM
- will bring to the month MARCH
But what is DD
? It's the number of the days from the beginning of the year.
So here it moved back to 8th day on this year (2018) which means January 8th.
That's why you are seeing January instead of March.
simple date format giving wrong month
Change the first format to
SimpleDateFormat tempFormat = new SimpleDateFormat("yyyy-MM-dd");
as DD
is the day in the year. 22
is definitely in January
Why is SimpleDateFormat parsing Date with wrong Month and Day?
DD
is wrong. D
is day of year. Sixth day of year is January 6.
You should use dd
.
Docs: SimpleDateFormat
SimpleDateFormat parsing wrong date
tl;dr
myJavaUtilDate
.toInstant()
.atZone
(
ZoneId.of( "Asia/Kolkata" )
)
.toLocalDate()
.isEqual
(
LocalDate
.parse
(
"03/10/2020" , // Do you mean March 10th, or October 3rd?
DateTimeFormatter.ofPattern( "dd/MM/uuuu" ) // Or "MM/dd/uuuu".
)
)
Smart objects, not dumb strings
You said:
make 3 dates of the same format so that I can compare them
Use objects with comparison methods, rather than comparing text of strings.
We have a class for dates built into Java: LocalDate
.
java.time
You are using Date
which is one of the terrible date-time classes bundled with the earliest versions of Java. These classes are now obsolete, supplanted years ago with the adoption of JSR 310 that defines the java.time classes.
I have passed a date
When encountering a java.util.Date
object, immediately convert to its modern replacement, java.time.Instant
. Use the new conversion method toInstant
added to the old class.
Instant instant = myJavaUtilDate.toInstant() ;
Both java.util.Date
and java.time.Instant
represent a moment in UTC. Is that how you want to perceive the date, in UTC with an offset of zero hours-minutes-seconds from the prime meridian? Keep in mind that for any given moment the date varies around the globe by zone. A moment may be "tomorrow" in Tokyo Japan while still "yesterday" in Toledo Ohio US.
OffsetDateTime odt = instant.atOffset( ZoneOffset.UTC ) ;
Extract the date.
LocalDate ld = odt.toLocalDate() ; // Extract the date only, omitting the time-of-day and the offset-from-UTC.
Or did you want to perceive that date in a particular zone?
ZoneId z = ZoneId.of( "Asia/Tokyo" ) ;
ZonedDateTime zdt = instant.atZone( z ) ;
LocalDate ld = zdt.toLocalDate() ; // Extract the date only, omitting the time-of-day and the zone.
and two string to a function
Define a formatting pattern to match your inputs.
String input = "03/10/2020" ;
DateTimeFormatter f = DateTimeFormatter.ofPattern( "dd/MM/uuuu" ) ;
LocalDate ld = LocalDate.parse( input , f ) ; // Throws `DateTimeParseException` if input is faulty.
Now compare, using methods isEqual
, isAfter
, isBefore
.
boolean datesMatch = ld1.isEqual( ld2 ) && ld2.isEqual( ld3 ) ;
java.util.Date::toString
tells a lie
You asked:
D2 = sat Oct 03 00:00:00 IST 2020 //wrong date fdate was 03/10/2020
Can anyone tell where did I go wrong?
Your main problem is that your formatting pattern is not defined to match your intention. This is correctly identified in the Answer by Chris and the Answer by Arvind Kumar Avinash.
In addition, you have another issue. Among the many problems with java.util.Date
is that its toString
method on-the-fly applies the JVM’s current default time zone while generating text to represent the content of the object. This creates the illusion of that zone being stored within the object. When perceiving your Date
object’s UTC value after adjusting to a time zone, the date may differ from the date as seen in UTC. This was discussed above.
➥ Never use java.util.Date
.
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date
, Calendar
, & SimpleDateFormat
.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310.
The Joda-Time project, now in maintenance mode, advises migration to the java.time classes.
You may exchange java.time objects directly with your database. Use a JDBC driver compliant with JDBC 4.2 or later. No need for strings, no need for java.sql.*
classes.
Where to obtain the java.time classes?
- Java SE 8, Java SE 9, Java SE 10, Java SE 11, and later - Part of the standard Java API with a bundled implementation.
- Java 9 adds some minor features and fixes.
- Java SE 6 and Java SE 7
- Most of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport.
- Android
- Later versions of Android bundle implementations of the java.time classes.
- For earlier Android (<26), the ThreeTenABP project adapts ThreeTen-Backport (mentioned above). See How to use ThreeTenABP….
Why does SimpleDateFormat() return wrong month?
As noted by other people, there are two problems in your current code:
- Months are zero based. So, month 7 is August, not July =\
- Year doesn't start by default at 1900 but at 1970, but if you set the year by yourself you'll get as year the same number you're setting, in this case, 75 (not 1975 as expected).
To solve this, you may create the GregorianCaledar
as new GregorianCaledar(1975, 6, 3)
. Or even better, stop working directly with this class and instead use the abstract class Calendar
:
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.YEAR, 1975);
calendar.set(Calendar.MONTH, Calendar.JULY);
calendar.set(Calendar.DATE, 3);
SimpleDateFormat df = new SimpleDateFormat("dd-MMM-yyyy");
String result = df.format(calendar.getTime());
System.out.println("fmt: " + result);
Why to use Calendar
instead of GregorianCalendar
? Because you should always work with abstract class/interface instead of class implementation.
Java SimpleDateFormat not detecting month
You are using the wrong date format string: DD
(day in year) instead of dd
(day in month). Change both SimpleDateFormat
instance to use dd
:
DateFormat inputFormat = new SimpleDateFormat("yyyyMMddhhmmss");
DateFormat outputFormat = new SimpleDateFormat("YYYY-MM-dd'T'hh:mm:ss'Z'");
Therefore you are getting the wrong result.
Getting wrong data when using SimpleDateFormat.parse()
You're using YYYY
in your format specifier, which is week year (as of Java 7, I believe). You want yyyy
, which is just "year". (See the SimpleDateFormat
documentation.)
I suspect the rest of the date was out because you tried to also specify the month and day, which aren't really "features" in the week year... if you'd specified the "week of week year" and day of week, it might have given some more sensible results, but only if you really meant to use week years, which I doubt :)
Java date format conversion - getting wrong month
Your fromFormat
uses minutes where it should use months.
String fromFormat = "yyyy-MM-dd";
Related Topics
Apache Httpclient Digest Authentication
Fragment Add or Replace Not Working
How to Close Another App in Android
What Is the Equivalent to a JavaScript Setinterval/Settimeout in Android/Java
How to Remove Only Trailing Spaces of a String in Java and Keep Leading Spaces
Theme.Appcompat.Light.Darkactionbar - No Resource Found
Google Cloud Messaging: Don't Receive Alerts When iOS App Is in Background
Is There an Advantage to Running Jruby If You Don't Know Any Java
Is Iterating Concurrenthashmap Values Thread Safe
Java Hotspot(Tm) 64-Bit Server Vm Warning: Ignoring Option Maxpermsize
Unhandled Exception Type Error
How to Simulate Low Memory in the Android Emulator
Why Menuitemcompat.Getactionprovider Returns Null
Transparent Blurry View Which Blurs Layout Underneath
Google Signin API Exception 10
Boot_Completed Not Working on Android 10 Q API Level 29