2017-02-11 8 views
0

私はかなり新しいJavaです。以下の形式でカレンダーを印刷するプログラムを作成しようとしています。現在の日付を使用してカレンダーを開始し、1カ月先のカレンダーのみを作成することになっています。コンソールでグレゴリオ暦を印刷する

Example: 

October 26, 2016. 

    Su  M  T  W  T  F  S 
       [October] 
|  |  |  |  | 27 | 28 | 29 | 
| 30 | 31 |  |  |  |  |  | 
       [November] 
|  |  | 1 | 2 | 3 | 4 | 5 | 
| 6 | 7 | 8 | 9 | 10 | 11 | 12 | 
| 13 | 14 | 15 | 16 | 17 | 18 | 19 | 
| 20 | 21 | 22 | 23 | 24 | 25 | 26 | 

私はできるだけ多くのことを書いていますが、実際のコーディングに着手する際には問題にぶつかります。たとえば、カレンダーを正しい曜日に開始する方法を見つけることができず、1か月で正しい週数を印刷するのに問題があります。 calendar = new GregorianCalendar()を使用するようにコードをやり直す必要がありますか?または、私は単にinstanceOf()を使用し、カレンダークラスを使いこなす必要がありますか?

これは、私のカレンダーを壊さずに書くことができるほどのコードです。

StringBuilder calendarString = new StringBuilder(); 
    Calendar calendar = Calendar.getInstance(); 
    int maxDaysOfMonth = calendar.getActualMaximum(Calendar.DAY_OF_MONTH); 
    int dayOfMonth = Calendar.DAY_OF_WEEK; 
    int weekOfMonth = Calendar.WEEK_OF_MONTH; 
    int theMonth = Calendar.MONTH; 
    String month; 

    switch(theMonth) { // Months start with 0 
    case 0: month = "January"; break; 
    case 1: month = "February"; break; 
    case 2: month = "March"; break; 
    case 3: month = "April"; break; 
    case 4: month = "May"; break; 
    case 5: month = "June"; break; 
    case 6: month = "July"; break; 
    case 7: month = "August"; break; 
    case 8: month = "September"; break; 
    case 9: month = "October"; break; 
    case 10: month = "November"; break; 
    default: month = "December"; break; 
    } 
    calendarString.append(month + " " + calendar.get(Calendar.DAY_OF_MONTH) + ", "); 
    calendarString.append(calendar.get(Calendar.YEAR) + "."); // First line ends here (Add Jobs this month) 
    calendarString.append(System.getProperty("line.separator")); 
    calendarString.append(System.getProperty("line.separator")); 
    calendarString.append(" Su "); 
    calendarString.append(" M "); 
    calendarString.append(" T "); 
    calendarString.append(" W "); 
    calendarString.append(" T "); 
    calendarString.append(" F "); 
    calendarString.append(" S "); 
    calendarString.append(System.getProperty("line.separator")); 

答えて

1

すべてでCalendar & GregorianCalendarクラスを使用するべきではありません。彼らは面倒で、混乱し、欠陥があり、うまく設計されていません。今すぐlegacyjava.timeクラスに置き換えられました。

LocalDate

LocalDateクラスは、時間日の時間帯なしなし日付専用の値を表しています。

タイムゾーンは、日付を決定する際に重要です。任意の瞬間について、日付は地球の周りでゾーンごとに異なります。たとえば、Paris Franceの真夜中の数分後には、新しい日がありますが、まだ「昨日」はMontréal Québecです。

は、America/MontrealAfrica/Casablanca、又はPacific/Aucklandとして、continent/regionの形式でproper time zone nameを指定します。 ESTまたはISTのような3〜4文字の略語は、ではなく、のように、標準化されておらず、ユニークではない(!)と使用しないでください。

ZoneId z = ZoneId.of("America/Montreal"); 
LocalDate today = LocalDate.now(z); 

日付を増分するには、一度に1日追加するだけです。

LocalDate nextDay = today.plusDays(1); 

DayOfWeek

あなたはDayOfWeek列挙オブジェクトとして曜日のために調べることができます。

DayOfWeek dayOfWeek = today.getDayOfWeek(); 

デイ・オブ・月

そして、あなたは日のヶ月(日付番号)のために調べることができます。

int dayOfMonth = today.getDayOfMonth(); 

月名

あなたは自動的にMonth列挙型を使用してローカライズされた月の名前を取得することができます。したがって、そのスイッチの必要はありませんswitch(theMonth)あなたのサンプルコードに見られる。ちなみに、java.timeは、従来のCalendarクラスに見られる狂った0-11ではなく、1月〜12月の1〜12ヶ月の数字になります。月

String monthName = today.getMonth().getDisplayName(TextStyle.FULL , Locale.CANADA_FRENCH); 

週は私が困っ月

の数を知る必要がありませんで週の正しい量を印刷しています。一度に1日増やすと、次の日が次の月に切り替わるときに確認してください。これを行う簡単な方法の1つは、YearMonthオブジェクトとして印刷されている月を追跡することです。

YearMonth ym = YearMonth.from(today); 
… 
YearMonth ymNextDay = YearMonth.from(nextDay); 
if (ymNextDay.isAfter(ym)) { 
    … print your next month name here 

あなただけの現在の月、あなたは終了月を決定する必要があるより多くのヶ月をしたいので。あなたの場合、それは翌月になります。そのような数学はYearMonthクラスで行うことができます。

YearMonth ymStop = ymStart.plusMonths(1); // Go from first month to the following month. 

問題を解決する方法は複数あります。代わりの方法では実際に週数を計算することができます。私はそうすることがあなたの特定の問題を複雑にすると思われます。単純に数える週

の正しい日にカレンダーを起動する方法

生成ブランク

最初の日付が木曜日で、日曜日を曜日の最初の曜日と見なす場合は、出力の最初の4つのスロット(列)に対して「空白」(すべてのスペース文字)を作成する必要があります。

世界で一般的な月曜日とISO 8601規格の場合は、DayOfWeek::getValueを呼び出してDayOfWeekに注文番号を問い合わせてください1から7です。月曜日でなければ、週の始まりからの日数を数える別の方法が必要です。 Listを使用して、目的の曜日を追跡することができます。

リスト内の位置を要求すると、0から始まるインデックス番号が返されます。だから1週間以内に序列を取得するために1つを追加します。空白を生成するために - あなたがループに4回(1 4 = 5)が必要です知っているので、

int dayNumber = daysOfWeekInOrder.indexOf(today.getDayOfWeek()) + 1 ; 

木曜日のために、あなたは、5を取得します。月の最後の日が月曜日である場合

同様に、あなたは5を取得するために7から差し引き、2を取得し、月曜日の日数を求めることができるので、あなたは、あなたが月に完了するために、5つの空白を生成する必要があります知っています。 java.timeについて


java.timeフレームワークは、Java 8に組み込まれており、後にされています。これらのクラスは面倒古いlegacy日時クラスなどjava.util.DateCalendar、& SimpleDateFormatに取って代わります。

maintenance modeにあるJoda-Timeプロジェクトは、java.timeクラスへの移行を推奨しています。

詳しくはOracle Tutorialをご覧ください。そして、多くの例と説明のためにStack Overflowを検索してください。仕様はJSR 310です。

ここで、java.timeクラスを取得するには?

  • Java SE 8SE 9以降
    • 内蔵しています。
    • バンドルされた実装の標準Java APIの一部です。
    • Java 9には、いくつかのマイナーな機能と修正が加えられています。
  • Java SE 6SE 7
    • java.time機能の多くはThreeTen-BackportのJava 6 & 7に戻って、移植されます。
  • Android
      ThreeTenABP
    • プロジェクトは、具体的にはAndroid用(上記)ThreeTen-バックポートを適応させます。
    • How to use ThreeTenABP…を参照してください。

ThreeTen-Extraプロジェクトでは、追加のクラスでjava.timeを拡張します。このプロジェクトは、将来のjava.timeへの追加の可能性を証明する土台です。ここでは、IntervalYearWeekYearQuartermoreなどの便利なクラスがあります。

関連する問題