体験を伝える―『ガジェット通信』の考え方

面白いものを探しにいこう 本物を体験し体感しよう 会いたい人に会いに行こう 見たことのないものを見に行こう そしてそれをやわらかくみんなに伝えよう [→ガジェ通についてもっと詳しく] [→ガジェット通信フロアについて]

【謎解きプログラム】正しいコードは?【仮想くじ引き】解答と解説

【謎解きプログラム】正しいコードは?【仮想くじ引き】

本問題は、表題のテーマで、プログラムにちなんだ謎を解くというものでした。

それでは以下、各問題とその解答を見ていきましょう。

問題のオープニング

ある日、出社すると、あなたのPCのログイン画面に、謎の挑戦状が表示されていた。

「24時間以内に謎が解けない場合は、このPCのデータは消失する。

 謎は、あなたが真のプログラマーなら解けるものだ」

これは挑戦状ではなく脅迫状だ!

そこには、見たことのない謎が掲載されていた。

あなたは歴戦のプログラマーとして、データを救うために、この謎に挑むことになった。

問題1

あなたは、抽象化された「くじ引き」の動作を、プログラムで書くことになりました。「くじ引き」は、1等賞~4等賞の賞品が入った10個の箱から、1つの箱を手に入れるものとします。

示されるコードは、C、Java、JavaScriptなどのプログラミング言語で見られるような、一般的な書き方のコードです。

要求動作を満たすコードを、選択肢から1つ選んで下さい。

● 要求動作

ランダムで1つ箱を選ぶ

● ルール

arr = getLotArr(); …… この処理は、以下の「くじ」の配列を得る。
arr[0] = 1;
// 1等賞 1つ
arr[1] = 2;
// 2等賞 2つ
arr[2] = 2;
// 2等賞
arr[3] = 3;
// 3等賞 3つ
arr[4] = 3;
// 3等賞
arr[5] = 3;
// 3等賞
arr[6] = 4;
// 4等賞 4つ
arr[7] = 4;
// 4等賞
arr[8] = 4;
// 4等賞
arr[9] = 4;
// 4等賞
len(arr) …… 配列arrの配列長を得る。
random() …… この関数は、0~999999の範囲のランダムな整数を戻す。
println() …… 引数を標準出力に出力する。

● コードと選択肢

// コード
arr = getLotArr();

res = arr[random()];
// 選択肢1
res = arr[random() % len(arr)];
// 選択肢2
res = arr[random() % len(arr) + 1]; // 選択肢3

println(res);

● 答え

配列の中から、ランダムで1つの要素を選ぶ処理です。

選択肢1では、関数「random()」の戻り値を添え字にしています。関数「random()」の戻り値は、0~999999の範囲のランダムな整数と定義されています。この数字に対して、配列の要素数は10しかありません。存在しない要素を得ようとしています。選択肢1は要求された動作になりません。

// 選択肢1
res = arr[random()];

res = arr[《0~999999の範囲のランダムな整数》];

選択肢2では、選択肢1とは違い、関数「random()」の戻り値の剰余を取っています。「len(arr)」は配列の要素数を戻すため「10」です。10の剰余を取れば値は「0~9」になり、存在する要素だけを得られます。選択肢2は要求された動作になります。

// 選択肢2
res = arr[random() % len(arr)];

res = arr[《0~999999の範囲のランダムな整数》 % 《10》];

res = arr[《0~9の範囲のランダムな整数》];

選択肢3では、選択肢2と違い、剰余を取ったあとに1を足しています。そのため配列の添え字が「1~10」になります。要素10は存在しないので、選択肢3は要求された動作になりません。

// 選択肢3
res = arr[random() % len(arr) + 1];

res = arr[《0~999999の範囲のランダムな整数》 % 《10》 + 1];

res = arr[《0~9の範囲のランダムな整数》 + 1];

res = arr[《1~10の範囲のランダムな整数》];

というわけで選択肢2の「res = arr[random() % len(arr)];」が答えになります。

以下、コードを、JavaScriptで処理したものを掲載します。

● 確認コード

// 共通
var res, i, sz, pos;
var arr = [];
var println = function() {
console.log(JSON.stringify(arguments[0]));
}
var random = function() {
return Math.floor(Math.random() * 1000000);
};
var len = function(arr) {
return arr.length;
};
var splt = function() {
console.log(‘——————–‘);
};

// くじの配列を初期化
var getLotArr = function() {
arr[0] = 1;
// 1等賞 1つ
arr[1] = 2;
// 2等賞 2つ
arr[2] = 2;
// 2等賞
arr[3] = 3;
// 3等賞 3つ
arr[4] = 3;
// 3等賞
arr[5] = 3;
// 3等賞
arr[6] = 4;
// 4等賞 4つ
arr[7] = 4;
// 4等賞
arr[8] = 4;
// 4等賞
arr[9] = 4;
// 4等賞
return arr;
};

//—————————————-
// ランダムで1つ箱を選ぶ。

// 選択肢1
console.log(‘選択肢1’);
(function() {
arr = getLotArr();
for (i = 0; i < 10; i ++) {
res = arr[random()]; // 選択肢1
println(res);
}
})();
splt();

// 選択肢2
console.log('選択肢2');
(function() {
arr = getLotArr();
for (i = 0; i < 10; i ++) {
res = arr[random() % len(arr)]; // 選択肢2
println(res);
}
})();
splt();

// 選択肢3
console.log('選択肢3');
(function() {
arr = getLotArr();
for (i = 0; i < 10; i ++) {
res = arr[random() % len(arr) + 1]; // 選択肢3
println(res);
}
})();
splt();

1 2 3 4次のページ
CodeIQ MAGAZINEの記事一覧をみる
  • 誤字を発見した方はこちらからご連絡ください。
  • ガジェット通信編集部への情報提供はこちらから
  • 記事内の筆者見解は明示のない限りガジェット通信を代表するものではありません。