如何在java中为iCal google-rfc-2445重复每年2月最后一天的日期
我需要在2月的最后一天重复一个日期,我使用Joda time来使用规则生成天、周、月等的日期。月工作正常,但大约几年后我收到错误的输出如何在java中为iCal google-rfc-2445重复每年2月最后一天的日期,java,jodatime,icalendar,rfc2445,Java,Jodatime,Icalendar,Rfc2445,我需要在2月的最后一天重复一个日期,我使用Joda time来使用规则生成天、周、月等的日期。月工作正常,但大约几年后我收到错误的输出 private static List<DateTime> calculateRecurrentDates(DateTime startDate, String recurrentRule) { List<DateTime> dates = new ArrayList<DateTime>(); TimeStam
private static List<DateTime> calculateRecurrentDates(DateTime startDate, String recurrentRule) {
List<DateTime> dates = new ArrayList<DateTime>();
TimeStamp startDate = Timestamp.valueOf("2011-02-28 10:10:10");
String recurrentRule = "RRULE:FREQ=YEARLY;COUNT=6;INTERVAL=1;";
String leapYearRule = "RRULE:FREQ=YEARLY;COUNT=6;INTERVAL=1;BYMONTHDAY=28,29;BYSETPOS=-1";
try {
DateTimeIterable range = DateTimeIteratorFactory.createDateTimeIterable(recurrentRule, startDate, DateTimeZone.UTC, true);
for (DateTime date : range) {
dates.add(date);
}
} catch (ParseException e) {
dates = null;
logger.error(e.getMessage());
}
return dates;
}
私有静态列表calculateRecurrentDates(日期时间开始日期,字符串循环中心){
列表日期=新建ArrayList();
TimeStamp startDate=TimeStamp.valueOf(“2011-02-28 10:10:10”);
String recurentrule=“RRULE:FREQ=year;COUNT=6;INTERVAL=1;”;
字符串leapYearRule=“RRULE:FREQ=year;COUNT=6;INTERVAL=1;BYMONTHDAY=28,29;BYSETPOS=-1”;
试一试{
DateTimeIterable范围=DateTimeIteratorFactory.createDateTimeIterable(Recurentrule,startDate,DateTimeZone.UTC,true);
用于(日期时间日期:范围){
日期。添加(日期);
}
}捕获(解析异常){
日期=空;
logger.error(例如getMessage());
}
返回日期;
}
但我收到的是:
2011-02-28 10:10:10.000Z2012-02-28 10:10:10.000Z
2013-02-28 10:10:10.000Z
2014-02-28 10:10:10.000Z
2015-02-28 10:10:10.000Z
2016-02-28 10:10:10.000Z
如果今年是闰年: 2012-02-29T10:10:10.000Z
2012-12-29T10:10:10.000Z
2013-12-29T10:10:10.000Z
2014-12-29T10:10:10.000Z
2015-12-29T10:10:10.000Z
2016-12-29T10:10:10.000Z
2017-12-29T10:10:10.000Z
我如何写一条规则来计算每年2月的最后一天?从3月1日减去一天
DateTimeZone timeZone = DateTimeZone.forID( "Europe/Paris" );
DateTime firstOfMarch = new DateTime( "2014-03-01", timeZone ).withTimeAtStartOfDay();
DateTime lastOfFebruary = firstOfMarch.minusDays( 1 ).withTimeAtStartOfDay();
在
firstOfMarch
对象上,调用plusYears(1)
继续向前。我的解决方案是从一年的最后一天到3月1日前一天进行计数。所以规则是这样的:
"RRULE:FREQ=YEARLY;COUNT=6;INTERVAL=1;BYYEARDAY=-307"
如果您只想操纵日期,请不要使用DateTimes,LocalDate是正确的类 如果你真的想得到二月的最后几天:
public static List<LocalDate> getLastDaysOfFebruary(LocalDate start, int n) {
ArrayList<LocalDate> list = new ArrayList<>();
LocalDate firstMar = start.withMonthOfYear(3).withDayOfMonth(1);
if(! firstMar.isAfter(start)) firstMar = firstMar.plusYears(1);
for(int i=0;i<n;i++) {
list.add(firstMar.minusDays(1));
firstMar = firstMar.plusYears(1);
}
return list;
}
公共静态列表getLastDaysof二月(LocalDate开始,int n){
ArrayList=新建ArrayList();
LocalDate firstMar=开始时间,每年(3)个月,每月(1)个月;
如果(!firstMar.isAfter(start))firstMar=firstMar.plusYears(1);
对于(int i=0;i如果你想确保你在一个月的最后一天得到一个事件,你应该使用
BYMONTHDAY=-1
(请参阅),然后确保它只发生在2月份BYMONTH=2
,然后给出:
RRULE:FREQ=YEARLY;BYMONTH=2;BYMONTHDAY=-1
然后,由于您提到了COUNT
属性,您还可以定义UNTIL
,它指定您希望对RRULE
进行评估的时间:
RRULE:FREQ=YEARLY;BYMONTH=2;BYMONTHDAY=-1;UNTIL=20200302T070000Z
找到3月1日,然后减去1天,这是我做类似事情的方式。你真的需要一个带时间的日期还是一个普通的日期?如果是更晚的,不要使用DateTime,使用LocalDate。