Calendar rightNow = Calendar.getInstance();
String month = String.valueOf(rightNow.get(Calendar.MONTH));
После выполнения вышеприведенного фрагмента, месяц получает значение 10 вместо 11. Как получилось?
Calendar rightNow = Calendar.getInstance();
String month = String.valueOf(rightNow.get(Calendar.MONTH));
После выполнения вышеприведенного фрагмента, месяц получает значение 10 вместо 11. Как получилось?
Месяцы индексируются от 0 не 1, поэтому 10 - это ноябрь, а 11 - декабрь.
Они начинаются с 0 - проверяют документы
Как видно из многих ответов: месяц начинается с 0.
Вот совет: вы должны использовать SimpleDateFormat для получения строкового представления месяца:
Calendar rightNow = Calendar.getInstance();
java.text.SimpleDateFormat df1 = new java.text.SimpleDateFormat("MM");
java.text.SimpleDateFormat df2 = new java.text.SimpleDateFormat("MMM");
java.text.SimpleDateFormat df3 = new java.text.SimpleDateFormat("MMMM");
System.out.println(df1.format(rightNow.getTime()));
System.out.println(df2.format(rightNow.getTime()));
System.out.println(df3.format(rightNow.getTime()));
Вывод:
11
Nov
November
Примечание: выход может отличаться, он зависит от локали.
Как отметили несколько человек, месяцы, возвращенные Calendar и Date в Java индексируются от 0 вместо 1. Итак, 0 - январь, а текущий месяц, ноябрь - 10.
Вы можете удивиться, почему это так. Истоки лежат с стандартными функциями POSIX ctime
, gmtime
и localtime
, которые принимают или возвращают структуру time_t
со следующими полями: man 3 ctime):
int tm_mday; /* day of month (1 - 31) */
int tm_mon; /* month of year (0 - 11) */
int tm_year; /* year - 1900 */
Этот API был полностью скопирован в класс Java Date в Java 1.0, а оттуда, в основном, неповрежден в класс Calendar в Java 1.1. Солнце зафиксировало наиболее вопиющую проблему, когда они представили календарь - тот факт, что 2001 год в григорианском календаре был представлен значением 101 в их классе Date. Но я не уверен, почему они не меняли значения дня и месяца, по крайней мере, оба были последовательными в их индексировании, либо от нуля, либо от одного. Эта несогласованность и связанная с этим путаница все еще существуют в Java (и C) по сей день.
Месяцы начинаются с нуля, например индексы для списков.
Поэтому Jan = 0, Feb = 1 и т.д.
Из API:
Первый месяц года - ЯНВАРЬ который равен 0; последнее зависит от количество месяцев в году.
http://java.sun.com/j2se/1.5.0/docs/api/java/util/Calendar.html
LocalDate.now() // Returns a date-only `LocalDate` object for the current month of the JVM’s current default time zone.
.getMonthValue() // Returns 1-12 for January-December.
Другие ответы правильные, но устаревшие.
У неприятных старых классов времени было много плохих вариантов дизайна и недостатков. Один из них - это подсчет с нулевым числом чисел 0-11, а не очевидный 1-12.
Структура java.time встроена в Java 8 и более поздних версий. Эти классы вытесняют старые неудобные классы времени, такие как java.util.Date
, .Calendar
и java.text.SimpleDateFormat
.
Теперь в режиме обслуживания Joda-Time также советует перейти на java.time.
Чтобы узнать больше, см. Учебник Oracle. И поиск Qaru для многих примеров и объяснений.
Большая часть функциональных возможностей java.time портирована на Java 6 и 7 в ThreeTen-Backport и далее адаптирована для Android в ThreeTenABP.
Проект ThreeTen-Extra расширяет java.time с дополнительными классами. Этот проект является доказательством возможных будущих дополнений к java.time.
В java.time число месяца действительно ожидается 1-12 за январь-декабрь.
Класс LocalDate
представляет значение даты только без времени и без часового пояса.
LocalDate today = LocalDate.now( ZoneId.of( "America/Montreal" ) );
int month = today.getMonthValue(); // Returns 1-12 as values.
Если вы хотите использовать дату-время для часового пояса, используйте объект ZonedDateTime
таким же образом.
ZonedDateTime now = ZonedDateTime.now( ZoneId.of( "America/Montreal" ) );
int month = now.getMonthValue(); // Returns 1-12 as values.
Если у вас есть объект GregorianCalendar
, перейдите в ZonedDateTime
, используя новый toZonedDateTime
добавлен в старый класс. Для получения дополнительной информации о конверсиях см. Преобразовать java.util.Date в тип "java.time" ?
ZonedDateTime zdt = myGregorianCalendar.toZonedDateTime();
int month = zdt.getMonthValue(); // Returns 1-12 as values.
Month
enumВ классы java.time входят удобные Month
enum, кстати. Используйте экземпляры этого класса в коде, а не просто целые, чтобы сделать ваш код более самодокументированным, обеспечить тип безопасности и обеспечить допустимые значения.
Month month = today.getMonth(); // Returns an instant of `Month` rather than integer.
В перечислении Month
перечислены полезные методы, такие как создание строки с локализованное имя месяца.
cal.get(Calendar.MONTH) + 1;
В приведенном выше утверждении указано точное число месяца. Поскольку get(Calendar.Month)
возвращает месяц, начиная с 0, добавление 1 к результату даст правильный результат. И помните, чтобы вычесть 1 при установке месяца.
cal.set(Calendar.MONTH, (8 - 1));
Или используйте постоянные переменные.
cal.set(Calendar.MONTH, Calendar.AUGUST);
Лучше использовать
Calendar.JANUARY
который равен нулю...
currentDateTime.get(Calendar.MONTH + 1)
Calender.Month return Целое число от 0 до 11, чтобы показать григорианский месяц вы должны прибавить 1 к Calander.MONTH