How to find week of the month - java

I like to know which week of the month a particular day falls. For example 20-Sep-2012 falls on 4th week of September but the below code displays it as 3 which is not correct. The system is dividing the days by 7 and returning the output and which is not I require. I have searched in Joda API's but not able to find the solution. Please let me know is there any way to figure out the week of a month, a day falls
Calendar ca1 = Calendar.getInstance();
ca1.set(2012,9,20);
int wk=ca1.get(Calendar.WEEK_OF_MONTH);
System.out.println("Week of Month :"+wk);

This is due to two reasons:
The first one is this (from the API):
The first week of a month or year is defined as the earliest seven day period beginning on getFirstDayOfWeek() and containing at least
getMinimalDaysInFirstWeek() days
The default value for this varies (mine was 4), but you can set this to your preferred value with
Calendar.setMinimalDaysInFirstWeek()
The second reason is the one #Timmy brought up in his answer. You need to perform both changes for your code to work. Complete working example:
public static void main(String[] args) {
Calendar ca1 = Calendar.getInstance();
ca1.set(2012, Calendar.SEPTEMBER, 20);
ca1.setMinimalDaysInFirstWeek(1);
int wk = ca1.get(Calendar.WEEK_OF_MONTH);
System.out.println("Week of Month :" + wk);
}
This prints
Week of Month :4

Month is zero-based. So ca1.set(2012,9,20) is actually setting the calendar to October.

To get sure the right month is set try using the month-constants provided by the Calendar-Class.

For those working with Joda time, this is what I am using:
/**
* For a week starting from Sunday, get the week of the month assuming a
* valid week is any week containing at least one day.
*
* 0=Last,1=First,2=Second...5=Fifth
*/
private int getWeekOfMonth( MutableDateTime calendar )
{
long time = calendar.getMillis();
int dayOfMonth = calendar.getDayOfMonth();
int firstWeekday;
int lastDateOfMonth;
int week;
int weeksInMonth;
calendar.setDayOfMonth( 1 );
firstWeekday = calendar.getDayOfWeek();
if (firstWeekday == 7)
{
firstWeekday = 0;
}
calendar.setHourOfDay( 0 );
calendar.addMonths( 1 );
calendar.addDays( -1 );
lastDateOfMonth = calendar.getDayOfMonth();
weeksInMonth = (int)Math.ceil( 1.0*(lastDateOfMonth + firstWeekday)/7 );
week = (byte)(1 + (dayOfMonth + firstWeekday - 1)/7);
week = (week == weeksInMonth)?0:week;
calendar.setMillis( time );
return week;
}

I'm very late to this question, but I feel the full answer is missing, which is, that how weeks are interpreted can differ quite a lot depending on the Locale.
The question seems to need the settings for the US (or a similar Locale), which uses 1 as minimal days in first week, and Sunday as the first day of the week.
The question, and all the answers take a default Calendar instance which comes with 4 as minimal days in first week, and Monday as first day of the week.
A simple demo program shows this :
public static void main(String[] args) {
{
System.out.println("--- ISO ---");
Calendar calendar = Calendar.getInstance();
System.out.println("First day of week : " + calendar.getFirstDayOfWeek());
System.out.println("Minimal days in 1st week : " + calendar.getMinimalDaysInFirstWeek());
calendar.set(2012, Calendar.SEPTEMBER, 20);
int wk = calendar.get(Calendar.WEEK_OF_MONTH);
System.out.println("Week of Month : " + wk);
}
{
System.out.println("--- USA ---");
Calendar calendar = Calendar.getInstance(Locale.US);
System.out.println("First day of week : " + calendar.getFirstDayOfWeek());
System.out.println("Minimal days in 1st week : " + calendar.getMinimalDaysInFirstWeek());
calendar.set(2012, Calendar.SEPTEMBER, 20);
int wk = calendar.get(Calendar.WEEK_OF_MONTH);
System.out.println("Week of Month : " + wk);
}
}
And that yields this output :
--- ISO ---
First day of week : 2
Minimal days in 1st week : 4
Week of Month : 3
--- USA ---
First day of week : 1
Minimal days in 1st week : 1
Week of Month : 4
CONCLUSION :
There's no need to manually set the minimal days in first week, or the first day of week. Just make sure you're using the right Locale.
Extra
Joda time only had support for ISO weeks.
Since Java 8 and the new time API you can go about it like this :
LocalDate localDate = LocalDate.of(2012, 9, 20);
TemporalField usWeekOfMonth = WeekFields.of(Locale.US).weekOfMonth();
TemporalField isoWeekOfMonth = WeekFields.ISO.weekOfMonth();
System.out.println("USA week of month " + usWeekOfMonth.getFrom(localDate));
System.out.println("ISO week of month " + usWeekOfMonth.getFrom(localDate));
Output :
USA week of month 4
ISO week of month 4
And there's even support in the formatter :
DateTimeFormatter usDateTimeFormatter = DateTimeFormatter.ofPattern("W/MM")
.withLocale(Locale.US);
System.out.println("USA formatter : " + usDateTimeFormatter.format(localDate));
DateTimeFormatter isoDateTimeFormatter = DateTimeFormatter.ofPattern("W/MM");
System.out.println("ISO formatter : " + isoDateTimeFormatter.format(localDate));
Output :
USA formatter : 4/09
ISO formatter : 3/09

class test {
public static void main(String[] args){
Calendar cal = Calendar.getInstance();
cal.set(2016, Calendar.AUGUST, 01);
printDayOFWeek(cal, Calendar.MONDAY, 5);//prints monday on 5th week
}
}
private static void printDayOFWeek(Calendar cal, int day, int whatweek) {
cal.set(Calendar.DAY_OF_WEEK, day);//day = Mon, tue, wed,..etc
cal.set(Calendar.DAY_OF_WEEK_IN_MONTH, -1); //-1 return last week
Date last = cal.getTime();
cal.set(Calendar.DAY_OF_WEEK_IN_MONTH, whatweek);
Date one = cal.getTime();
if(one.before(last) || one.compareTo(last) ==0)
{
System.out.println(whatweek +"WEEK" + cal.getTime());
}
}

Related

When trying to get last date of next month getting last date of next month of next year in java

Trying to run this code it was working perfectly fine till OCT but in NOV it is like
firstdate 2019-12-01 & lastdate 2020-12-31
public class Test1 {
public static void main(String[] args) {
Calendar calendar = Calendar.getInstance();
calendar.add(Calendar.MONTH, 1);
String date;
calendar.set(Calendar.DATE,calendar.getActualMinimum(Calendar.DAY_OF_MONTH));
Date nextMonthFirstDay = calendar.getTime();
date=new SimpleDateFormat("YYYY-MM-dd").format(nextMonthFirstDay).toLowerCase();
System.out.println("firstdate "+ date);
calendar.set(Calendar.DAY_OF_MONTH,calendar.getActualMaximum(Calendar.DAY_OF_MONTH));
Date nextMonthLastDay = calendar.getTime();
date=new SimpleDateFormat("YYYY-MM-dd").format(nextMonthLastDay).toLowerCase();
System.out.println("lastdate "+date);
}
}
I don't know why it is showing like this..
Is it a fault or bug in java ?
Change your date format to yyyy-MM-dd (notice lowercase for year)
They both represent a year but yyyy represents the calendar year while YYYY represents the year of the week.
So something like...
date=new SimpleDateFormat("yyyy-MM-dd").format(nextMonthLastDay).toLowerCase();
Hope it helps!
You seem to already have got an answer that works, however, here is one that uses the modern datetime API java.time and is s little more readable than the way you are calculating the first and last day of the next month based on today:
public static void main(String[] args) {
// base is today
LocalDate today = LocalDate.now();
/*
* create a LocalDate from
* - the year of next month (may be different)
* - the current month plus 1 and
* - the first day
* ——> first day of next month
*/
LocalDate firstDayOfNextMonth = LocalDate.of(
today.plusMonths(1).getYear(),
today.getMonth().plus(1),
1);
/*
* create a LocalDate from
* - the first day of next month (just created above)
* - add a month and
* - subtract one day
* ——> last day of next month
*/
LocalDate lastDayOfNextMonth = firstDayOfNextMonth.plusMonths(1).minusDays(1);
// print the results
System.out.println("first date of upcoming month:\t"
+ firstDayOfNextMonth.format(DateTimeFormatter.ISO_DATE));
System.out.println("last date of upcoming month:\t"
+ lastDayOfNextMonth.format(DateTimeFormatter.ISO_DATE));
}
Don't be misled by the formatting, there are significantly fewer lines of code and their output is
first date of upcoming month: 2019-12-01
last date of upcoming month: 2019-12-31

Getting the week number for a date (week starting on Wednesday)

LocalDate initial = LocalDate.now();
DayOfWeek dayOfWeek = DayOfWeek.WEDNESDAY;
WeekFields weekFields = WeekFields.of(dayOfWeek, 1);
int weekNo = date.get(weekFields.weekOfWeekBasedYear());
System.out.println("Week No"+weekNo);
I am using the above code for date 2018-07-29. I expect week no 30, but I get 31.
What am I missing here to get the result of 30?
If you expected output as according to ISO-8601, where current week is week 30, you'd need to follow this:
Week number according to the ISO-8601 standard, weeks starting on Monday. The first week of the year is the week that contains that year's first Thursday (='First 4-day week').
This is implemented by WeekFields.ISO.
If instead, you want the week to start on WEDNESDAY, you only need to change the minimalDaysInFirstWeek from 1 to 4 (='First 4-day week'):
LocalDate date = LocalDate.now();
WeekFields weekFields = WeekFields.of(DayOfWeek.WEDNESDAY, 4);
int weekNo = date.get(weekFields.weekOfWeekBasedYear());
System.out.println("Week No " + weekNo);

get the start and end dates of the week using java [duplicate]

This question already has answers here:
Get last week date range for a date in Java
(5 answers)
Closed 5 years ago.
My requirement is to get the start and end date of the week when date is passed. I have searched and i found tons of answers but confused with which one is best to use.In one of the thread i found the below code:
Calendar c = Calendar.getInstance();
c.setTime(new Date("8/16/2017"));
int dayOfWeek = c.get(Calendar.DAY_OF_WEEK);
System.out.println("day :" + dayOfWeek);
c.set(Calendar.DAY_OF_WEEK, c.getFirstDayOfWeek());
System.out.println("start of week day :" + c.getTime());
output:
day :4
start of week day :Sun Aug 13 00:00:00 EDT 2017
I see a bug in the above code output. Start of the week should be Monday Aug14 but it shows Sun Aug13. Any suggestions to get the start date and end date of the week when date is passed as a String dynamically.
--EDITED--
I'm looking for java code which returns the first and last day date's of the week when date is passed.
import java.time.LocalDate;
import static java.time.DayOfWeek.MONDAY;
import static java.time.DayOfWeek.SUNDAY;
import static java.time.temporal.TemporalAdjusters.nextOrSame;
import static java.time.temporal.TemporalAdjusters.previousOrSame;
public class FirstAndLast
{
public static void main(String[] args)
{
LocalDate today = LocalDate.now();
LocalDate monday = today.with(previousOrSame(MONDAY));
LocalDate sunday = today.with(nextOrSame(SUNDAY));
System.out.println("Today: " + today);
System.out.println("Monday of the Week: " + monday);
System.out.println("Sunday of the Week: " + sunday);
}
}
Calendar c = Calendar.getInstance();
c.setFirstDayOfWeek(Calendar.MONDAY); //Line2
c.setTime(new Date("8/16/2017"));
int dayOfWeek = c.get(Calendar.DAY_OF_WEEK);
System.out.println("day :" + dayOfWeek);
c.set(Calendar.DAY_OF_WEEK, c.getFirstDayOfWeek());
System.out.println("start of week day :" + c.getTime());
Set the first day of the week to Monday as in line 2.
Now the output will be
day :4
start of week day :Mon Aug 14 00:00:00 EDT 2017

How to get the date of a specific day in a specific week

I wanto to get the date of a specific day in a specific week, identified by the week number.
Here's an example:
Today it is Monday (03.10.2016) and it is the week with the number 58.
Now i want to get the date of e.g. Friday of this week.
I use Joda-Time within my android application.
Currently Iam creating a LocalDate.
// This is the date of today
private LocalDate reportDate = new LocalDate();
// The number of the week is calculated here
int week = Weeks.weeksBetween(startDate.dayOfWeek().withMinimumValue().minusDays(1),
reportDate.dayOfWeek().withMaximumValue().plusDays(1)).getWeeks();
switch(day_of_week) {
case "Monday":
// Get date of this day in current week
break;
case "Tuesday":
// Get date of this day in current week
break;
// ...
You can use following code to achieve the days as desired,
LocalDateTime yourDate = LocalDateTime.now();
System.out.println(yourDate.getWeekOfWeekyear());
int weekOfyear = yourDate.getWeekOfWeekyear();
//Fetch Week Start Date for Given Week Number
DateTime weekStartDate = new DateTime().withWeekOfWeekyear(weekOfyear);
System.out.println(weekStartDate.toString());
//Fetch Specific Days for given week
DateTime wedDateTime = weekStartDate.withDayOfWeek(DateTimeConstants.WEDNESDAY);
I hope this answer your query.
As per my understanding of your requirement I have implemented below code, just check if it helps you,
First Import Calendar Package As Below
import java.util.Calendar;
Now Create below function
public String getSpecificDate(int weekOfYear, int dayOfWeek)
{
Calendar cal = Calendar.getInstance();
cal.set(Calendar.WEEK_OF_YEAR, weekOfYear);
cal.set(Calendar.DAY_OF_WEEK, dayOfWeek);
int year = cal.get(Calendar.YEAR);
int month = cal.get(Calendar.MONTH); // 0 to 11
int day = cal.get(Calendar.DAY_OF_MONTH);
String selectedDate = " " + day + "-" + (month+1) + "-" + year;
return selectedDate;
}
// I have passed getSpecificDate(41, 6) and get 7-10-2016 as output

Why is my printed date wrong?

I have verified that the date is read correctly from a file, but once I use SimpleDateFormat.format with the pattern "dd/MM/yy" it suddenly adds a month. This leads me to believe lenient mode is calculating the wrong value. But I have no idea what would make it add a full month.
Some example dates I read:
16/09/2013
23/09/2013
30/09/2013
07/10/2013
14/10/2013
21/10/2013
The code used to parse the date (it's a wrapper around Calendar I made):
public static SimpleDateTime parseDate(String date)
{
String[] dateParts = date.split("[-\\.:/]");
int day = Integer.parseInt(dateParts[0]);
int month = Integer.parseInt(dateParts[1]);
int year = Integer.parseInt(dateParts[2]);
return new SimpleDateTime(dag, maand, jaar);
}
The constructor used here:
public SimpleDateTime(int day, int month, int year)
{
date = Calendar.getInstance();
date.setLenient(true);
setDay(day);
setMonth(month);
setYear(year);
}
The setters for day, month and year:
public void setYear(int year)
{
date.set(Calendar.YEAR, year);
}
public void setMonth(int month)
{
date.set(Calendar.MONTH, month);
}
public void setDay(int day)
{
date.set(Calendar.DAY_OF_MONTH, day);
}
And the code used to format the date:
public String toString(String pattern)
{
String output = new SimpleDateFormat(pattern, Locale.getDefault()).format(date.getTime());
return output;
}
where the pattern passed is:
"dd/MM/yy"
Intended to print a date as:
16/09/13
23/09/13
Instead I get:
16/10/13
23/10/13
January is 0 in Java; February is 1 and so on.
See Calendar.JANUARY, Calendar.FEBRUARY.
So when you're reading 1 from the file
you think you read JAN but you read FEB.
You should do: date.set(Calendar.MONTH, month-1); to fix this.
Months are indexed from 0 not 1 so 10 is November and 11 will be December.
Calendar.MONTH
From documentation:
Field number for get and set indicating the month. This is a calendar-specific value. The first month of the year is JANUARY; the last depends on the number of months in a year.
So if you check JANUARY you see it starts in zero.
Make sure your month is in the interval 0-11. Possibly it is in 1-12.
The reason for this is that the counting starts at 0.
January == 0
February == 1
and so on. See the documentation.
THe problem is that you pass 9 to SimpleDateFormat and since month are indexed from 0 to 11 it will parse month '9' as the 10th month.
You need to subtract 1 from the month :)
Calendar class in Java holds months starting from 0, hence when you set the month as 0, it would consider it as January. SimpleDateFormat provides for a way to correctly display the value as 01.
Calendar cal = Calendar.getInstance();
cal.set(Calendar.MONTH, 0);
System.out.println(new SimpleDateFormat("dd/MM/yy").format(cal.getTime()));
Output:
29/01/14
The workaround for you to align you file that Calendar can work with (since December - or 12 would trickle over to the next year) or modify your logic to pick Constants like:
cal.set(Calendar.MONTH, Calendar.JANUARY);
The answer by peter.petrov is almost correct, except for one major problem. Like your question, it neglects to account for time zone.
For your information, this kind of work is much easier in Joda-Time (or new java.time.* classes in Java 8). Joda-Time is so much cleaner you won't even feel the need to create a wrapper class.
// Specify the time zone for which the incoming date is intended.
DateTimeZone timeZone = DateTimeZone.forID( "Europe/Brussels" );
String input = "16/09/2013";
DateTimeFormatter formatter = DateTimeFormat.forPattern("dd/MM/yyyy").withZone( timeZone );
DateTime dateTime = formatter.parseDateTime( input );
String output = formatter.print( dateTime );
Dump to console…
System.out.println( "dateTime: " + dateTime );
System.out.println( "output: " + output );
System.out.println( "millis since Unix epoch: " + dateTime.getMillis() );
When run…
dateTime: 2013-09-16T00:00:00.000+02:00
output: 16/09/2013
millis since Unix epoch: 1379282400000

Categories

Resources