web-dev-qa-db-ja.com

特定の月の週数を取得したい

今月の週数を取得したいのですが、先週の前月日と翌月の最初の週日を含みます。

このようなもの:

Simple Isnt it?

Androidの特定のグリッドビューアダプターでこれを使用したいので、このコードブロックを操作しようとしています:

            //FIRST_DAY_OF_WEEK =0;
    int lastDay = month.getActualMaximum(Calendar.DAY_OF_MONTH);
    int firstDay = (int) month.get(Calendar.DAY_OF_WEEK);
    int firstDayNextMonth = nextMonth.get(Calendar.DAY_OF_WEEK);
    int lastDayNextMonth=nextMonth.getActualMaximum(Calendar.DAY_OF_MONTH);
    int nextMonthdays=nextMonth.getMinimalDaysInFirstWeek();

    // figure size of the array
    if (firstDay == 1) {
        days = new String[lastDay + (FIRST_DAY_OF_WEEK * 6)];
    }

    else {
        days = new String[lastDay + firstDay - (FIRST_DAY_OF_WEEK + 1)];
    }
17
Nezam

CalendarクラスのWEEK_OF_YEAR属性が役立ちます。参照: カレンダークラス

ある月の最初の日となる新しい日付を作成します。この日の年の週を取得します。開始値を取得したとします。

指定された月の最終日となる新しい日付を作成します。この日の年の週を取得すると、最終値が得られます。

ここで終了-開始+1はあなたが望むものでなければなりません。

週が別の年などと重なる場合は、いくつかのコーナーケースを処理する必要がある場合があります。しかし、これを正しく理解すれば、単純なロジックでそれを実行できると思います。

これが簡単なサンプルコードです。それを機能させて、好きなものを渡すことができると思います。

        Calendar cal = Calendar.getInstance();
        cal.set(Calendar.YEAR, 2013);
        cal.set(Calendar.MONTH, 1);
        cal.set(Calendar.DAY_OF_MONTH, 1);
        int start = cal.get(Calendar.WEEK_OF_YEAR);
        Log.d("BLA BLA", "Value is " + start);
        cal.set(Calendar.YEAR, 2013);
        cal.set(Calendar.MONTH, 1);
        cal.set(Calendar.DAY_OF_MONTH, 28);
        int end = cal.get(Calendar.WEEK_OF_YEAR);
        //Above line will not work for December Month, use following line for this
        int end = isDecember?53:cal.get(Calendar.WEEK_OF_YEAR);
        Log.d("BLA BLA", "Value is " + end);
        Log.d("BLA BLA", "Num weeks:: " + (end - start +1 ));

コーナーケースの場合:

コーナーケースはJanuarayの月(例:2010年1月、2000年1月)にのみ発生します。これらの場合、ほとんどの日は前年の最終週の一部であるため、開始値は52、終了値は5になります。これが発生するかどうかを確認します。

          if(start > end) {
                numweeks = end + 1;
             }

追伸:あなたが得たさまざまなテスト入力にそれを入れてください。何か問題が見つかったら、改善できるかどうか教えてください。

そしてさらに簡単な解決策:

        Calendar cal = Calendar.getInstance();
        for(int i = 0 ; i < 11;i++){
            cal.set(Calendar.YEAR, 2013);
            cal.set(Calendar.DAY_OF_MONTH, 1);
            cal.set(Calendar.MONTH, i);
            int maxWeeknumber = cal.getActualMaximum(Calendar.WEEK_OF_MONTH);
            Log.d("LOG","max week number" + maxWeeknumber);
        }

        01-22 01:49:03.591: D/LOG(573): max week number5
        01-22 01:49:03.602: D/LOG(573): max week number5
        01-22 01:49:03.602: D/LOG(573): max week number6
        01-22 01:49:03.671: D/LOG(573): max week number5
        01-22 01:49:03.671: D/LOG(573): max week number5
        01-22 01:49:03.671: D/LOG(573): max week number6
        01-22 01:49:03.681: D/LOG(573): max week number5
        01-22 01:49:03.691: D/LOG(573): max week number5
        01-22 01:49:03.691: D/LOG(573): max week number5
        01-22 01:49:03.711: D/LOG(573): max week number5
        01-22 01:49:03.711: D/LOG(573): max week number5

単純な解決策はコーナーケースでうまく機能します:

        Calendar cal = Calendar.getInstance();
        for(int i = 0 ; i < 11;i++){
            cal.set(Calendar.YEAR, 2010);
            cal.set(Calendar.DAY_OF_MONTH, 1);
            cal.set(Calendar.MONTH, i);
            int maxWeeknumber = cal.getActualMaximum(Calendar.WEEK_OF_MONTH);
            // Month value starts from 0 to 11 for Jan to Dec
            Log.d("LOG","For Month :: "+ i + " Num Week :: " + maxWeeknumber);
        }

ログ:

        01-22 01:59:35.841: D/LOG(629): For Month :: 0 Num Week :: 6
        01-22 01:59:35.841: D/LOG(629): For Month :: 1 Num Week :: 5
        01-22 01:59:35.841: D/LOG(629): For Month :: 2 Num Week :: 5
        01-22 01:59:35.841: D/LOG(629): For Month :: 3 Num Week :: 5
        01-22 01:59:35.841: D/LOG(629): For Month :: 4 Num Week :: 6
        01-22 01:59:35.852: D/LOG(629): For Month :: 5 Num Week :: 5
        01-22 01:59:35.871: D/LOG(629): For Month :: 6 Num Week :: 5
        01-22 01:59:35.871: D/LOG(629): For Month :: 7 Num Week :: 5
        01-22 01:59:35.871: D/LOG(629): For Month :: 8 Num Week :: 5
        01-22 01:59:35.871: D/LOG(629): For Month :: 9 Num Week :: 6
        01-22 01:59:35.871: D/LOG(629): For Month :: 10 Num Week :: 5
10
VendettaDroid

wEEK_OF_MONTHを使用する方が適切であり、年をまたがる問題はありません。

public static void main(String[] args) throws Exception {
  for (String m : new String[] { "2012-11", "2012-12", "2013-01", "2013-02", "2013-03",
              "2013-04", "2013-05", "2013-06" }) {
      SimpleDateFormat format = new SimpleDateFormat("yyyy-MM");
      Date date = format.parse(m);
      Calendar c = Calendar.getInstance();
      c.setTime(date);

      int start = c.get(Calendar.WEEK_OF_MONTH);

      c.add(Calendar.MONTH, 1);
      c.add(Calendar.DATE, -1);
      int end = c.get(Calendar.WEEK_OF_MONTH);
      System.out.println(" # of weeks in " + format.format(c.getTime())
              + ": " + (end - start + 1));
  }
}

結果:

# of weeks in 2012-11: 5
# of weeks in 2012-12: 6
# of weeks in 2013-01: 5
# of weeks in 2013-02: 5
# of weeks in 2013-03: 6
# of weeks in 2013-04: 5
# of weeks in 2013-05: 5
# of weeks in 2013-06: 6
7
zzzhc

カレンダークラスを使用して、次のようなことを行うことができます

Calendar calendar = Calendar.getInstance();
System.out.println(calendar.getActualMaximum(Calendar.WEEK_OF_MONTH));

これにより、当月の週数が返されます

6
Vardaan Sharma

「手」でやりたいなら

これを使って:

Date.prototype.getMonthWeek = function(monthAdjustement)
{    

    var firstDay = new Date(this.getFullYear(), this.getMonth(), 1).getDay();

    var returnMessage = (Math.ceil(this.getDate()/7) + Math.floor(((7-firstDay)/7)));

    return returnMessage;

}

ここで、monthAdjustementは、今日の日付と比較して、探している月を調整する単なる整数です。

0

月の最初の日(土曜日、日曜日など)がわかっていると仮定します。

  • 月の1日がSundayであり、うるう年ではない場合、(修正編集)February月は4週間しかありません。それ以外の場合は、すべての場合で、少なくとも5週間、最大で6週間必要です。
  • これで、月がSaturdayで始まる場合、常に6週間になります(2月の場合を除き、5週間になります)。
  • これで、月がFridayで始まる場合、31日の月は6週間、その他の月は5週間になります。
  • それ以外の場合は、常に5週間になります。

月の1日を見つけるのは難しいことではありません。Calendarまたは他の日付/時刻ユーティリティライブラリクラスを使用できます。ただし、コーナーケースや不要な複雑さを取り除く、よりクリーンなソリューションがあると思います。

0
Swapnil