获得当前的年份和月份导致奇怪的结果

我正在研究一个与Android相关的学习项目。 我想通过使用下面的代码来获得当前的年份和月份,但它不适合我。

GregorianCalendar gc = new GregorianCalendar(); gc.YEAR // returning 1 gc.MONTH // returning 2 Calendar c = Calendar.getInstance(); c.YEAR // returning 1 c.MONTH // returning 2 

有人能帮我吗? 难道我做错了什么? 请原谅我,我是新的Java开发。 谢谢。

Solutions Collecting From Web of "获得当前的年份和月份导致奇怪的结果"

只是为了给更多的背景:

new GregorianCalendar()Calendar.getInstance()都会正确给出在当前date和时间初始化的日历。

MONTHYEARCalendar类中的常量 。 你不应该使用“通过”引用,使它看起来像是对象状态的一部分。 这是Calendar类devise的一个不幸的部分,为了访问不同字段的值,需要使用一个字段号来调用get并将其指定为其中一个常量,如其他答案所示:

 Calendar c = Calendar.getInstance(); int year = c.get(Calendar.YEAR); int month = c.get(Calendar.MONTH); 

请注意,月份编号为0,所以在撰写本文时(4月份)月份编号将为3。

这是Java语言devise的一个不幸的部分,您可以通过该types的expression式引用静态成员(例如常量),而不是通过types名称。

我的build议是:

  • 如果您的IDE允许它(如Eclipse所做的那样),则使诸如c.YEARexpression式会产生编译时错误 – 如果您始终使用Calendar.YEAR则代码c.YEAR清晰。
  • 在可能的情况下,使用Joda Time–一个更好的Javadate/时间库。 无可否认,在Android上你可能会有一些空间限制,但是如果你的应用程序做了大量的date/时间操作,那么会为你节省很多麻烦。

注意MONTHS从0开始。因此,如果您需要将其映射到实际问题,只需添加+1即可

 int month=c.get(Calendar.MONTH)+1; 
 int year=c.get(Calendar.YEAR); int month=c.get(Calendar.MONTH); System.out.println(year); System.out.println(month); 

TL;博士

 YearMonth.now( ZoneId.of( "America/Montreal" ) ) 

细节

Jon Skeet的答案是正确的。 你正在访问常量而不是询问你自己的对象。

这是一个完全不同的select,使用现代date时间课程。

避免遗留的date时间类

诸如java.util.Datejava.util.Calendarjava.text.SimpleTextFormat类的旧date时间类现在是遗留的 ,被java.time类取代。

YearMonth

如果您专注于没有date的年份和月份,没有时间,也没有时区,请使用YearMonth类。

而不是在年份和月份周围传递整数,传递这个类的对象。 这样做可以提供types安全性,确保有效的值,并使您的代码更加自我logging。

确定当前年份和月份意味着确定当前date。 而且对于这个时区来说至关重要。 对于任何特定的时刻,date在全球各地按照地区而不同。

 ZoneId z = ZoneId.of( "America/Montreal" ); YearMonth ym = YearMonth.now( z ); 

你可以询问它的部分。

 int year = ym.getYear(); int month = ym.getMonthValue(); 

这个课程提供方便的方法,比如告诉你这是不是一个闰年。 你可以做math,如加/减月/年。 你可以得到今年的任何一天的date。 和更多。

Month

而不是乱七八月整数,我build议你使用Month枚举。 这个class有十几个预定义的实例,每年一个月。 如上所述,使用对象为您提供了types安全性,有效值和自我logging代码。

 Month m = ym.getMonth(); 

该类具有有用的方法,例如生成一个带有月份名称的本地化string。


关于java.time

java.time框架内置于Java 8及更高版本中。 这些类取代了麻烦的旧的遗留date时间类,如java.util.DateCalendarSimpleDateFormat

Joda-Time项目现在处于维护模式 ,build议迁移到java.time类。

要了解更多信息,请参阅Oracle教程 。 并search堆栈溢出了很多例子和解释。 规范是JSR 310 。

从何处获取java.time类?

  • Java SE 8SE 9及更高版本
    • 内置。
    • 带有捆绑实现的标准Java API的一部分。
    • Java 9增加了一些小function和修复。
  • Java SE 6SE 7
    • 大部分的java.timefunction都被移植到了ThreeTen-Backport中的 Java 6&7中。
  • Android的
    • ThreeTenABP项目专门针对Android,采用了ThreeTen-Backport (上文提到)。
    • 请参阅如何使用…。
 Calendar c= Calendar.getInstance() int cyear = c.get(Calendar.YEAR);//calender year starts from 1900 so you must add 1900 to the value recevie.ie, 1990+112 = 2012 int cmonth = c.get(Calendar.MONTH);//this is april so you will receive 3 instead of 4. int cday = c.get(Calendar.DAY_OF_MONTH); 

参考这个链接

如何获得当前的年份和月份。

  Calendar calendar = Calendar.getInstance(); int month = calendar.get(Calendar.MONTH) + 1; int year = calendar.get(Calendar.YEAR); 

添加1得到正确的月份非常重要,因为第一个月的值是0:

  int month = calendar.get(Calendar.MONTH) + 1; 

:获取和设置月份的字段号。 这是一个日历特定的值。 阳历和朱利安年历的第一个月是一月,这是一月; 最后一个取决于一年中的月数。