Integer를 Java에서 지역화 된 월 이름으로 어떻게 변환 할 수 있습니까?


99

정수를 얻고 다양한 로케일의 월 이름으로 변환해야합니다.

로케일 en-us의 예 :
1-> 1 월
2 일-> 2 월

로케일 es-mx의 예 :
1-> Enero
2-> Febrero


5
주의하세요. Java 월은 0 기반이므로 0 = 1 월, 1 = 2 월 등
Nick Holt

당신이 옳습니다. 언어를 변경해야하는 경우에는 로케일 만 변경하면됩니다. 감사합니다
atomsfat

2
@NickHolt UPDATE 최신 java.timeMonth열거 형은 1부터 12 월까지 1-12입니다. [ java.time.DayOfWeek](https://docs.oracle.com/javase/9/docs/api/java/time/DayOfWeek.html): 1-7 for Monday-Sunday per ISO 8601 standard. Only the troublesome old legacy date-time classes such as 캘린더 `의 경우 에도 미친 번호 매기기 체계가 있습니다. 레거시 클래스를 피해야하는 여러 이유 중 하나는 이제 java.time 클래스로 완전히 대체되었습니다 .
Basil Bourque

답변:


211
import java.text.DateFormatSymbols;
public String getMonth(int month) {
    return new DateFormatSymbols().getMonths()[month-1];
}

12
배열이 0 기반이기 때문에 'month-1'이 필요하지 않습니까? atomsfat는 1-> 1 월 등을 원합니다.
Brian Agnew

7
그는 월 1이 필요합니다. 월은 0부터 시작하는 어레이 위치로 변환해야하는 1부터 시작하는 월 번호이기 때문입니다
Sam Barnum

5
public String getMonth (int month, Locale locale) {return DateFormatSymbols.getInstance (locale) .getMonths () [month-1]; }
atomsfat

4
그는 필요합니다 month-1. 다른 사용하는 사람은 Calendar.get(Calendar.MONTH)바로해야합니다month

1
DateFormatSymbols 구현이 JDK 8에서 변경되었으므로 getMonths 메소드가 더 이상 모든 로케일에 대해 올바른 값을 리턴하지 않습니다. oracle.com/technetwork/java/javase/…
ahaaman 2014

33

독립형 월 이름에는 LLLL을 사용해야합니다. 이것은 다음 SimpleDateFormat과 같은 문서에 문서화되어 있습니다.

SimpleDateFormat dateFormat = new SimpleDateFormat( "LLLL", Locale.getDefault() );
dateFormat.format( date );

JDK 1.7 /IllegalArgumentException : Illegal pattern character 'L'
AntJavaDev

26

tl; dr

Month                             // Enum class, predefining and naming a dozen objects, one for each month of the year. 
.of( 12 )                         // Retrieving one of the enum objects by number, 1-12. 
.getDisplayName(
    TextStyle.FULL_STANDALONE , 
    Locale.CANADA_FRENCH          // Locale determines the human language and cultural norms used in localizing. 
)

java.time

Java 1.8 (또는 ThreeTen-Backport 가있는 1.7 및 1.6 )부터 다음을 사용할 수 있습니다.

Month.of(integerMonth).getDisplayName(TextStyle.FULL_STANDALONE, locale);

integerMonth1 기반 1 월입니다 즉. 범위는 1 월 -12 월의 경우 항상 1-12입니다 (예 : 그레고리력 만 해당).


게시 한 방법을 사용하여 프랑스어로 5 월의 문자열 월이 있다고 가정 해 봅시다 (5 월 프랑스어는 Mai).이 문자열에서 5 번을 어떻게 얻을 수 있습니까 ??
usertest

@usertest 전달 된 지역화 된 월 이름 문자열에서 개체 를 가져 오기 위해 AnswerMonthDelocalizer 에 대략적인 초안 클래스 를 작성 했습니다. → Month.MAY. 대소 문자 구분이 중요합니다. 프랑스어 에서는는 유효하지 않으며 . MonthmaiMaimai
Basil Bourque

2019 년입니다.이게 어떻게 최고 답변이 아니죠?
anothernode

16

SimpleDateFormat을 사용합니다. 누군가가 월별 달력을 만드는 더 쉬운 방법이 있다면 나를 바로 잡으십시오. 나는 지금 코드에서 이것을하고 나는 그렇게 확신하지 않습니다.

import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.GregorianCalendar;


public String formatMonth(int month, Locale locale) {
    DateFormat formatter = new SimpleDateFormat("MMMM", locale);
    GregorianCalendar calendar = new GregorianCalendar();
    calendar.set(Calendar.DAY_OF_MONTH, 1);
    calendar.set(Calendar.MONTH, month-1);
    return formatter.format(calendar.getTime());
}

이 끔찍한 클래스는 이제 레거시, 현대에 의해 완전히 대체 있습니다 java.time의 JSR 310에 정의 된 클래스
바질 우르 큐

14

내가 할 방법은 다음과 같습니다. 범위 확인은 int month당신에게 맡기겠습니다 .

import java.text.DateFormatSymbols;

public String formatMonth(int month, Locale locale) {
    DateFormatSymbols symbols = new DateFormatSymbols(locale);
    String[] monthNames = symbols.getMonths();
    return monthNames[month - 1];
}

12

SimpleDateFormat 사용.

import java.text.SimpleDateFormat;

public String formatMonth(String month) {
    SimpleDateFormat monthParse = new SimpleDateFormat("MM");
    SimpleDateFormat monthDisplay = new SimpleDateFormat("MMMM");
    return monthDisplay.format(monthParse.parse(month));
}


formatMonth("2"); 

결과 : 2 월


7

분명히 Android 2.2에는 SimpleDateFormat에 버그가 있습니다.

월 이름을 사용하려면 리소스에서 직접 정의해야합니다.

<string-array name="month_names">
    <item>January</item>
    <item>February</item>
    <item>March</item>
    <item>April</item>
    <item>May</item>
    <item>June</item>
    <item>July</item>
    <item>August</item>
    <item>September</item>
    <item>October</item>
    <item>November</item>
    <item>December</item>
</string-array>

그런 다음 다음과 같이 코드에서 사용하십시오.

/**
 * Get the month name of a Date. e.g. January for the Date 2011-01-01
 * 
 * @param date
 * @return e.g. "January"
 */
public static String getMonthName(Context context, Date date) {

    /*
     * Android 2.2 has a bug in SimpleDateFormat. Can't use "MMMM" for
     * getting the Month name for the given Locale. Thus relying on own
     * values from string resources
     */

    String result = "";

    Calendar cal = Calendar.getInstance();
    cal.setTime(date);
    int month = cal.get(Calendar.MONTH);

    try {
        result = context.getResources().getStringArray(R.array.month_names)[month];
    } catch (ArrayIndexOutOfBoundsException e) {
        result = Integer.toString(month);
    }

    return result;
}

"분명히 Android 2.2에는 버그가 있습니다." — 버그가 추적되는 위치에 연결할 수 있으면 유용합니다.
Peter Hall

6

tl; dr

Month.of( yourMonthNumber )           // Represent a month by its number, 1-12 for January-December. 
  .getDisplayName(                    // Generate text of the name of the month automatically localized. 
      TextStyle.SHORT_STANDALONE ,    // Specify how long or abbreviated the name of month should be.
      new Locale( "es" , "MX" )       // Locale determines (a) the human language used in translation, and (b) the cultural norms used in deciding issues of abbreviation, capitalization, punctuation, and so on.
  )                                   // Returns a String.

java.time.Month

이러한 성가신 오래된 레거시 날짜-시간 클래스를 대체하는 java.time 클래스에서 이제 훨씬 쉽게 수행 할 수 있습니다.

Month열거 다스 객체, 각 달을 정의합니다.

월은 1 월에서 12 월까지 1-12로 번호가 매겨집니다.

Month month = Month.of( 2 );  // 2 → February.

객체에 자동으로 현지화 된 월 이름의 문자열을 생성하도록 요청합니다 .

을 조정하여 TextStyle이름의 길이 또는 약자를 지정합니다. 일부 언어 (영어가 아님)에서는 월 이름이 단독으로 사용되거나 완전한 날짜의 일부로 사용되는 경우 달라집니다. 따라서 각 텍스트 스타일에는 …_STANDALONE변형이 있습니다.

Locale결정하려면 a 를 지정하십시오 .

  • 번역에 사용해야하는 인간 언어.
  • 약어, 구두점 및 대문자와 같은 문제를 결정해야하는 문화적 규범

예:

Locale l = new Locale( "es" , "MX" );
String output = Month.FEBRUARY.getDisplayName( TextStyle.SHORT_STANDALONE , l );  // Or Locale.US, Locale.CANADA_FRENCH. 

이름 → Month개체

참고로, 다른 방향으로 이동 ( Month열거 형 개체 를 얻기 위해 월 이름 문자열 구문 분석 )은 기본 제공되지 않습니다. 이를 위해 자신의 클래스를 작성할 수 있습니다. 그런 수업에 대한 나의 빠른 시도가 있습니다. 자신의 책임하에 사용하십시오 . 나는이 코드에 진지한 생각이나 테스트를하지 않았다.

용법.

Month m = MonthDelocalizer.of( Locale.CANADA_FRENCH ).parse( "janvier" ) ;  // Month.JANUARY

암호.

package com.basilbourque.example;

import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import java.time.Month;
import java.time.format.TextStyle;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;

// For a given name of month in some language, determine the matching `java.time.Month` enum object.
// This class is the opposite of `Month.getDisplayName` which generates a localized string for a given `Month` object.
// Usage… MonthDelocalizer.of( Locale.CANADA_FRENCH ).parse( "janvier" ) → Month.JANUARY
// Assumes `FormatStyle.FULL`, for names without abbreviation.
// About `java.time.Month` enum: https://docs.oracle.com/javase/9/docs/api/java/time/Month.html
// USE AT YOUR OWN RISK. Provided without guarantee or warranty. No serious testing or code review was performed.
public class MonthDelocalizer
{
    @NotNull
    private Locale locale;

    @NotNull
    private List < String > monthNames, monthNamesStandalone; // Some languages use an alternate spelling for a “standalone” month name used without the context of a date.

    // Constructor. Private, for static factory method.
    private MonthDelocalizer ( @NotNull Locale locale )
    {
        this.locale = locale;

        // Populate the pair of arrays, each having the translated month names.
        int countMonthsInYear = 12; // Twelve months in the year.
        this.monthNames = new ArrayList <>( countMonthsInYear );
        this.monthNamesStandalone = new ArrayList <>( countMonthsInYear );

        for ( int i = 1 ; i <= countMonthsInYear ; i++ )
        {
            this.monthNames.add( Month.of( i ).getDisplayName( TextStyle.FULL , this.locale ) );
            this.monthNamesStandalone.add( Month.of( i ).getDisplayName( TextStyle.FULL_STANDALONE , this.locale ) );
        }
//        System.out.println( this.monthNames );
//        System.out.println( this.monthNamesStandalone );
    }

    // Constructor. Private, for static factory method.
    // Personally, I think it unwise to default implicitly to a `Locale`. But I included this in case you disagree with me, and to follow the lead of the *java.time* classes. --Basil Bourque
    private MonthDelocalizer ( )
    {
        this( Locale.getDefault() );
    }

    // static factory method, instead of  constructors.
    // See article by Dr. Joshua Bloch. http://www.informit.com/articles/article.aspx?p=1216151
    // The `Locale` argument determines the human language and cultural norms used in de-localizing input strings.
    synchronized static public MonthDelocalizer of ( @NotNull Locale localeArg )
    {
        MonthDelocalizer x = new MonthDelocalizer( localeArg ); // This class could be optimized by caching this object.
        return x;
    }

    // Attempt to translate the name of a month to look-up a matching `Month` enum object.
    // Returns NULL if the passed String value is not found to be a valid name of month for the human language and cultural norms of the `Locale` specified when constructing this parent object, `MonthDelocalizer`.
    @Nullable
    public Month parse ( @NotNull String input )
    {
        int index = this.monthNames.indexOf( input );
        if ( - 1 == index )
        { // If no hit in the contextual names, try the standalone names.
            index = this.monthNamesStandalone.indexOf( input );
        }
        int ordinal = ( index + 1 );
        Month m = ( ordinal > 0 ) ? Month.of( ordinal ) : null;  // If we have a hit, determine the `Month` enum object. Else return null.
        if ( null == m )
        {
            throw new java.lang.IllegalArgumentException( "The passed month name: ‘" + input + "’ is not valid for locale: " + this.locale.toString() );
        }
        return m;
    }

    // `Object` class overrides.

    @Override
    public boolean equals ( Object o )
    {
        if ( this == o ) return true;
        if ( o == null || getClass() != o.getClass() ) return false;

        MonthDelocalizer that = ( MonthDelocalizer ) o;

        return locale.equals( that.locale );
    }

    @Override
    public int hashCode ( )
    {
        return locale.hashCode();
    }

    public static void main ( String[] args )
    {
        // Usage example:
        MonthDelocalizer monthDelocJapan = MonthDelocalizer.of( Locale.JAPAN );
        try
        {
            Month m = monthDelocJapan.parse( "pink elephant" ); // Invalid input.
        } catch ( IllegalArgumentException e )
        {
            // … handle error
            System.out.println( "ERROR: " + e.getLocalizedMessage() );
        }

        // Ignore exception. (not recommended)
        if ( MonthDelocalizer.of( Locale.CANADA_FRENCH ).parse( "janvier" ).equals( Month.JANUARY ) )
        {
            System.out.println( "GOOD - In locale "+Locale.CANADA_FRENCH+", the input ‘janvier’ parses to Month.JANUARY." );
        }
    }
}

java.time 정보

java.time의 프레임 워크는 나중에 자바 8에 내장되어 있습니다. 이 클래스는 까다로운 기존에 대신 기존 과 같은 날짜 - 시간의 수업을 java.util.Date, Calendar, SimpleDateFormat.

Joda 타임 프로젝트는 지금에 유지 관리 모드 의로 마이그레이션을 조언 java.time의 클래스.

자세한 내용은 Oracle Tutorial을 참조하십시오 . 그리고 많은 예제와 설명을 위해 Stack Overflow를 검색하십시오. 사양은 JSR 310 입니다.

java.time 객체를 데이터베이스와 직접 교환 할 수 있습니다 . JDBC 4.2 이상을 준수 하는 JDBC 드라이버를 사용하십시오 . 문자열이나 클래스 가 필요하지 않습니다 .java.sql.*

java.time 클래스는 어디서 구할 수 있습니까?

ThreeTen - 추가 프로젝트 추가 클래스와 java.time를 확장합니다. 이 프로젝트는 java.time에 향후 추가 될 수있는 가능성을 입증하는 곳입니다. 당신은 여기에 몇 가지 유용한 클래스와 같은 찾을 수 있습니다 Interval, YearWeek, YearQuarter, 그리고 .


1

getMonthName 메서드에 DateFormatSymbols 클래스를 사용하여 일부 Android 장치에서 월별 이름을 표시하는 이름을 가져올 때 문제가 있습니다. 이 방법으로이 문제를 해결했습니다.

String_array.xml에서

<string-array name="year_month_name">
    <item>January</item>
    <item>February</item>
    <item>March</item>
    <item>April</item>
    <item>May</item>
    <item>June</item>
    <item>July</item>
    <item>August</item>
    <item>September</item>
    <item>October</item>
    <item>November</item>
    <item>December</item>
    </string-array>

Java 클래스에서 다음과 같이이 배열을 호출하십시오.

public String[] getYearMonthName() {
        return getResources().getStringArray(R.array.year_month_names);
        //or like 
       //return cntx.getResources().getStringArray(R.array.month_names);
    } 

      String[] months = getYearMonthName(); 
           if (i < months.length) {
            monthShow.setMonthName(months[i] + " " + year);

            }

해피 코딩 :)


1

Kotlin 확장

fun Int.toMonthName(): String {
    return DateFormatSymbols().months[this]
}

용법

calendar.get(Calendar.MONTH).toMonthName()

끔찍한 Calendar클래스에 의해 년 전 대체되었다 java.time의 JSR 310에 정의 된 클래스
바질 우르 큐

0
    public static void main(String[] args) {
    SimpleDateFormat format = new SimpleDateFormat("MMMMM", new Locale("en", "US"));
    System.out.println(format.format(new Date()));
}

이것은 정답 인 것 같지만, 당신이하는 일과 왜 이런 식으로하는지 설명해 주시겠습니까?
마틴 프랭크

나는 단순하고 복잡하지 않다고 생각하기 때문에 이렇게한다!
Diogo Oliveira

그러나 그것은 악명 높고 오래되고 오래된 SimpleDateFormat클래스를 사용합니다 .
Ole VV

이 끔찍한 날짜 - 시간 클래스에 의해 년 전 대체되었다 java.time의 JSR 310에 정의 된 클래스
바질 우르 큐


0

이것을 매우 간단한 방법으로 사용하고 자신의 func처럼 부르십시오.

public static String convertnumtocharmonths(int m){
         String charname=null;
         if(m==1){
             charname="Jan";
         }
         if(m==2){
             charname="Fev";
         }
         if(m==3){
             charname="Mar";
         }
         if(m==4){
             charname="Avr";
         }
         if(m==5){
             charname="Mai";
         }
         if(m==6){
             charname="Jun";
         }
         if(m==7){
             charname="Jul";
         }
         if(m==8){
             charname="Aou";
         }
         if(m==9){
             charname="Sep";
         }
         if(m==10){
             charname="Oct";
         }
         if(m==11){
             charname="Nov";
         }
         if(m==12){
             charname="Dec";
         }
         return charname;
     }

1
이런 종류의 코드를 작성할 필요가 없습니다. Java에는 Month::getDisplayName.
Basil Bourque

이 상용구 코드를 작성할 필요가 없습니다. 위에 게시 된 내 답변을 확인하십시오.
Sadda Hussain
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.