Java 8时间API:如何parsing格式为“MM.yyyy”的string到LocalDate

我对Java 8时间API中的parsingdate有点不鼓励。

以前我可以很容易地写:

String date = "04.2013"; DateFormat df = new SimpleDateFormat("MM.yyyy"); Date d = df.parse(date); 

但是现在,如果我使用LocalDate并像这样做:

 String date = "04.2013"; DateTimeFormatter formatter = DateTimeFormatter.ofPattern("MM.yyyy"); LocalDate ld = LocalDate.parse(date, formatter); 

我收到一个exception:

 java.time.format.DateTimeParseException: Text '04' could not be parsed at index 0 java.time.format.DateTimeFormatter.parseResolved0(DateTimeFormatter.java:1948) java.time.format.DateTimeFormatter.parse(DateTimeFormatter.java:1850) java.time.LocalDate.parse(LocalDate.java:400) java.time.LocalDate.parse(LocalDate.java:385) com.luxoft.ath.controllers.JsonController.region(JsonController.java:38) sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) java.lang.reflect.Method.invoke(Method.java:483) org.springframework.web.method.support.InvocableHandlerMethod.invoke(InvocableHandlerMethod.java:215) org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:132) org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:104) org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandleMethod(RequestMappingHandlerAdapter.java:749) org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:689) org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:83) org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:938) org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:870) org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:961) org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:852) javax.servlet.http.HttpServlet.service(HttpServlet.java:617) org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:837) javax.servlet.http.HttpServlet.service(HttpServlet.java:723) org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88) org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 

如果我将string格式更改为“yyyy-MM-dd” ,即使没有格式化器,也可以完美地工作:

 String date = "2013-04-12"; LocalDate ld = LocalDate.parse(date); 

所以我的问题是:如何使用Java 8时间API自定义格式parsingdate?

这是有道理的:你的input不是一个真正的date,因为它没有一天的信息。 你应该把它parsing为一个YearMonth ,如果你不关心这一天, YearMonth使用这个结果。

 String date = "04.2013"; DateTimeFormatter formatter = DateTimeFormatter.ofPattern("MM.yyyy"); YearMonth ym = YearMonth.parse(date, formatter); 

如果您确实需要申请特定的一天,则可以从YearMonth获取LocalDate ,例如:

 LocalDate ld = ym.atDay(1); //or LocalDate ld = ym.atEndOfMonth(); 

例如,您也可以使用TemporalAdjuster作为该月的最后一天*:

 LocalDate ld = ym.atDay(1).with(lastDayOfMonth()); 

*用一个import static java.time.temporal.TemporalAdjusters.lastDayOfMonth;

下面的select可能不是很好,但至less也是一个成功的testing解决scheme,所以我在这里提到它的完整性和作为对@assylias正确答案的补充:

 DateTimeFormatterBuilder builder = new DateTimeFormatterBuilder(); builder.parseDefaulting(ChronoField.DAY_OF_MONTH, 1); builder.append(DateTimeFormatter.ofPattern("MM.yyyy")); DateTimeFormatter dtf = builder.toFormatter(); String ym = "04.2013"; LocalDate date = LocalDate.parse(ym, dtf); System.out.println(date); // output: 2013-04-01