こんにちは、私は小さな灰色の類人猿で、バグを書くことができるプログラマーです!
私のコラム「DailyBlueBridge」に注目してください。このコラムの主な機能は、近年のBlue Bridge Cupの地方大会と決勝戦の実際の質問を共有し、アルゴリズムのアイデア、データ構造、およびあなたが学ぶのを助けるためにそこに存在する他のコンテンツより多くの知識と技術に!
タイトル:サブキャンディ
輪になって座っている子供はn人います。先生は各子供にランダムに偶数のキャンディーを与え、次のゲームをします。
それぞれの子供は、左側の子供にキャンディーの半分を与えました。
砂糖を割った後、キャンディーの数が奇数の子供には、先生から偶数が与えられます。
すべての子供が同じ数のキャンディーを持つまで、このゲームを繰り返します。
あなたの仕事は、教師が既知の最初のキャンディーの下で再発行する必要があるキャンディーの数を予測することです。
【フォーマット要件】
プログラムは最初に、子の数を表す整数N(2 <N <100)を読み取ります。
スペースで区切られたN個の偶数の行(各偶数は1000以下、2以上)
プログラムは、教師が再発行する必要のあるキャンディーの数を示す整数を出力する必要があります。
例:次のように入力します
3
2 2 4
プログラムは次のように出力する必要があります。
4
リソース契約:
ピークメモリ消費量(仮想マシンを含む)<256M
CPU消費量<1000ms
要件に厳密に従って出力し、「入力してください...」などの余分なコンテンツを印刷しないでください。
すべてのコードは同じソースファイルに配置されます。デバッグに合格したら、ソースコードをコピーして送信します。
注:パッケージステートメントは使用しないでください。jdk1.6以降のバージョンの機能は使用しないでください。
注:メインクラスの名前はMainである必要があります。そうでない場合、無効なコードとして扱われます。
問題解決のアイデア:
この質問の考え方は非常に明確です。各子が所有するキャンディーの数を配列に格納し、whileループまたは再帰を使用して、ゲームの各ラウンドをプレイできます。ゲームの各ラウンドが終了した後、配列内の要素の数が等しいかどうかを判別します。
次に、whileループと再帰を使用して、この問題を個別に解決します。
回答のソースコード:
whileループメソッド
package 一四年省赛真题; import java.util.Scanner; public class Year2014_Bt8_2 { public static void main(String[] args) { Scanner scanner = new Scanner(System.in); int N = scanner.nextInt(); int[] arr = new int[N]; for (int i = 0; i < arr.length; i++) { arr[i] = scanner.nextInt(); } int ans = 0; while (true) { int firstN = arr[0]; for (int i = 0; i < arr.length; i++) { if (i==arr.length-1) { arr[i] = arr[i]/2 + firstN/2; } else { arr[i] = arr[i]/2 + arr[i+1]/2; } } //老师补发糖果 for (int i = 0; i < arr.length; i++) { //如果当前手中的糖果数量是奇数个 if (arr[i]%2!=0) { arr[i]+=1; ans++; } } //判断数组中的元素是否都相等 if (check(arr)) { System.out.println(ans); } } } //判断数组元素值是否都相等 private static boolean check(int[] arr) { for (int i = 0; i < arr.length; i++) { if (arr[i]!=arr[0]) { return false; } } return true; } } }
再帰
package 一四年省赛真题; import java.util.Scanner; public class Year2014_Bt8 { static int ans = 0; //记录补发的糖果数 public static void main(String[] args) { Scanner scanner = new Scanner(System.in); int N = scanner.nextInt(); int[] arr = new int[N]; for (int i = 0; i < arr.length; i++) { arr[i] = scanner.nextInt(); } f(arr); System.out.println(ans); } //每一轮游戏 private static void f(int[] arr) { int firstN = arr[0]; //记录第一个数组元素 //利用循环将每一个小朋友手中的糖果给左边的小朋友分一半 for (int i = 0; i < arr.length; i++) { if (i==arr.length-1) { arr[i] = arr[i]/2 + firstN/2; }else { arr[i] = arr[i]/2 + arr[i+1]/2; } } //老师补发糖果 for (int i = 0; i < arr.length; i++) { //如果当前手中的糖果数量是奇数个 if (arr[i]%2!=0) { arr[i]+=1; ans+=1; } } //判断数组中的元素是否都相等 if (check(arr)) { return; } //进行下一轮游戏 f(arr); } //判断数组元素值是否都相等 private static boolean check(int[] arr) { for (int i = 0; i < arr.length; i++) { if (arr[i]!=arr[0]) { return false; } } return true; } }
サンプル出力: