Java 如何查找给定月份的日期范围
我想找到给定月份列表的日期范围。我写的代码是Java 如何查找给定月份的日期范围,java,json,date,datetime,simpledateformat,Java,Json,Date,Datetime,Simpledateformat,我想找到给定月份列表的日期范围。我写的代码是 List<String> allDates = new ArrayList<>(); String maxDate = "2017-11-06"; SimpleDateFormat monthDate = new SimpleDateFormat("yyyy-MM-dd"); Calendar cal = Calendar.getI
List<String> allDates = new ArrayList<>();
String maxDate = "2017-11-06";
SimpleDateFormat monthDate = new SimpleDateFormat("yyyy-MM-dd");
Calendar cal = Calendar.getInstance();
cal.setTime(monthDate.parse(maxDate));
for (int i = 1; i <= 14; i++) {
String month_name1 = monthDate.format(cal.getTime());
allDates.add(month_name1);
cal.add(Calendar.MONTH, -1);
}
for (int j = 0; j < allDates.size() - 1; j++) {
JSONObject dateRange = new JSONObject();
dateRange.put("until", allDates.get(j));
System.out.println("to date:"+allDates.get(j));
dateRange.put("since", allDates.get(j + 1));
System.out.println("from date:"+ allDates.get(j + 1));
}
但我想以这种形式:
to date:2017-11-06
from date:2017-10-06
to date:2017-10-05
from date:2017-09-05
to date:2017-09-04
from date:2017-08-04
to date:2017-08-03
from date:2017-07-03
to date:2017-07-02
from date:2017-06-02
您每个月在allDates列表中只存储一个字符串,并尝试将其用作“截止日期”和“起始日期”,这两个日期将以相同的字符串结尾。您应该为每个截止日期和起始日期添加两个不同的字符串。我已相应地修改了您的循环:
for (int i = 1; i <= 14; i++) {
String month_name1 = monthDate.format(cal.getTime());
allDates.add(month_name1);
cal.add(Calendar.MONTH, -1);
month_name1 = monthDate.format(cal.getTime());
allDates.add(month_name1);
cal.add(Calendar.DATE, -1);
}
for (int j = 0; j < allDates.size() - 1; j+=2) {
JSONObject dateRange = new JSONObject();
dateRange.put("until", allDates.get(j));
System.out.println("to date:"+allDates.get(j));
dateRange.put("since", allDates.get(j + 1));
System.out.println("from date:"+ allDates.get(j + 1));
}
对于(int i=1;i每个范围只存储一个日期是可以的。标准方法是使用半开放范围,以便每个范围从一个包含的存储日期到下一个不包含的日期
我建议您存储日期而不是字符串。我发现每当需要字符串时,对日期进行格式化更为自然,而不是每次需要日期时解析字符串(并考虑任何解析异常)。
我全心全意地建议跳过过时的类
SimpleDateFormat
和Calendar
,并使用后者。正如您将看到的那样,后者更易于使用
java.time
的LocalDate
类非常适合我们在没有时间的情况下存储日期的需要。另一个优点是它的toString
方法生成一个类似于2017-10-06
的字符串,这是您在JSON对象中使用的格式,因此不再需要显式格式化程序(这可能不是巧合:该格式是ISO 8601标准的一部分,越来越多地用于交换日期和时间信息,尤其是JSON格式)。此外,LocalDate
比Calendar
加上和减去一天和一个月更自然,只要您记住每次都会创建一个新对象
// store only the start date of each range
List<LocalDate> allStartDates = new ArrayList<>();
// add 1 day ot the last end date to obtain the start day of the following range
LocalDate currentStartDate = LocalDate.of(2017, Month.NOVEMBER, 06).plusDays(1);
for (int i = 1; i <= 14; i++) {
allStartDates.add(currentStartDate);
currentStartDate = currentStartDate.minusDays(1).minusMonths(1);
}
for (int j = 1; j < allStartDates.size(); j++) {
JSONObject dateRange = new JSONObject();
// subtract 1 day from the start day of the following range
// to get the last day of this range
String endDate = allStartDates.get(j - 1).minusDays(1).toString();
dateRange.put("until", endDate);
System.out.println("to date:" + endDate);
String startDate = allStartDates.get(j).toString();
dateRange.put("since", startDate);
System.out.println("from date:" + startDate);
}
问题:我可以在Java版本中使用现代API吗?
如果至少使用Java6,则可以
- 在Java8和更高版本中,新的API是内置的
- 在Java6和7GET中,新类的后端口(Three-Ten for)
- 在Android上,使用Android版的ThreeTen Backport。它被称为ThreeTenABP,我认为这里面有一个很好的解释
任何一个特别的原因,为什么你仍然在与过时的类SimpleDateFormat
和Calendar
?一起工作是非常好的。尤其是在像你这样的最新算法方面。在2017-05-01到2017-06-01之间的范围内,你想要什么?从2017-04-30到2017-05-31之间的范围??
// store only the start date of each range
List<LocalDate> allStartDates = new ArrayList<>();
// add 1 day ot the last end date to obtain the start day of the following range
LocalDate currentStartDate = LocalDate.of(2017, Month.NOVEMBER, 06).plusDays(1);
for (int i = 1; i <= 14; i++) {
allStartDates.add(currentStartDate);
currentStartDate = currentStartDate.minusDays(1).minusMonths(1);
}
for (int j = 1; j < allStartDates.size(); j++) {
JSONObject dateRange = new JSONObject();
// subtract 1 day from the start day of the following range
// to get the last day of this range
String endDate = allStartDates.get(j - 1).minusDays(1).toString();
dateRange.put("until", endDate);
System.out.println("to date:" + endDate);
String startDate = allStartDates.get(j).toString();
dateRange.put("since", startDate);
System.out.println("from date:" + startDate);
}
to date:2017-11-06
from date:2017-10-06
to date:2017-10-05
from date:2017-09-05
to date:2017-09-04
from date:2017-08-04
to date:2017-08-03
from date:2017-07-03
to date:2017-07-02
from date:2017-06-02
to date:2017-06-01
from date:2017-05-01
to date:2017-04-30
from date:2017-03-30
to date:2017-03-29
from date:2017-02-28
to date:2017-02-27
from date:2017-01-27
to date:2017-01-26
from date:2016-12-26
to date:2016-12-25
from date:2016-11-25
to date:2016-11-24
from date:2016-10-24
to date:2016-10-23
from date:2016-09-23