VBAを使った乱数とその記録についての演習

へびせんせい

ボタンを押すことで、1から6までのランダムな数値を出力し、その値を記録するマクロを作成しなさい。
この演習では、ボタンを押したときのSubプロシージャーはすでに完成してるものとします。
下記の条件に従って、ユーザー定義関数として、乱数を発生する関数と値を記録する関数を作成しなさい。

演習問題の作成の流れ

乱数記録シートの画像

上の画像のように、ボタンを押したときに、乱数が作られ、その時の時刻と乱数の値を記録するマクロを作成する。
この演習問題では、ボタンをクリックしたときのマクロ(main関数と呼ぶ)はすでに作成されている。
main関数では、2つのFunction関数を呼びだし、それぞれの機能を実装していくこととする。

ボタンを押したときのマクロ(main関数)

Sub main_button_click()
  
  Dim rand_num As Long
  
  rand_num = GetRandomNumber(1, 6)
  
  Call RecordNumber(rand_num)
  
End Sub

main関数では、まず乱数を格納するための変数rand_numを定義している。
そして、GetRandomNumberというユーザー定義関数で、1から6までの乱数を取得している。

乱数が代入されたrand_numは、次に、RecordNumberという関数に送られる。
このRecordNumberは送られた値をセルに記録するための返り値なしのユーザー定義関数である。
記録したデータはセルを編集できないように自動的にロック(シートの保護)がかかるものとする。

つまりこの演習では、2つのFunction関数を作成するものである
このExcelファイルを使って、演習をすすめなさい

・main関数(main_button_click)は変更しないこと
・2つのFunction関数の中身を記載しなさい

Download

任意な範囲の乱数を発生するGetRandomNumber関数について

ExcelVBAでは、0から1までの実数の乱数をつくる関数は用意されているが、任意な範囲の整数の乱数ををつくる関数は用意されていない。
そこで、ユーザー定義関数として、作成することとする。

GetRandomNumberの引数や返り値はすでに決められており、次の通りである。

Function GetRandomNumber(minnum As Long, maxnum As Long) As Long
  'minnumからmaxnumまでの範囲の整数の乱数を返す関数(返り値あり)'

End Function
  • 引数minnumは発生させる乱数の最も小さい数値
  • 引数maxnumは発生させる乱数の最も大きい数値
  • 返り値はminnumからmaxnumまでの乱数をLong型で返す

今回は、main関数でminnumが1、maxnumが6と指定されているので、1から6までの整数の乱数を出力しなければならない。

Rnd関数について

Rnd関数は、擬似乱数を含む単精度浮動小数点型 (single) の値を返します。
その値は0以上1未満の値となります。

構文
Rnd(数値)

引数(数値)により、乱数のシードを指定することができますが、省略して構いません。

実際の使用例です。

Rnd関数の使用例

Rnd関数では、0以上1未満の値が返される。
仮にこの値を10倍して、整数にすれば、0から9の整数の乱数が返されることになる。
こういった計算をFunction関数の中で行うことで、minnumからmaxnumまでの整数の乱数を返す関数を作成する。

Randomizeステートメント

実はRnd関数は、Randomizeステートメントを事前に実行しておかないと、Excelを起動するたびに同じ値の乱数が出てしまう。
*おそらく、上のコードではExcel起動して一回目の乱数は0.7055...の値になるはず

そこで、Rnd関数を使う前に、

Randomize

この1行を加えるだけで、きちんと乱数になる。

Rnd関数の使用例

受け取った値を記録するRecordNumber関数について

GetRandomNumberで得られた乱数は、RecordNumber関数に送られ、セルに記録される。

RecordNumber関数の引数もすでに決められており、次の通りとする。

Function RecordNumber(recnum As Long)
  'recnumの値を送ると、A列にその時の時刻、B列にrecnumの値を記録する関数(返り値なし)'

End Function
  • 引数recnumは、得られた乱数を送ること
  • A列にこのマクロが動作した時刻、B列にrecnumが入力される
  • 記録したセルは消えないように、乱数を送るたびに次の行に記録すること
  • 返り値はないものとする
  • このマクロが動作することで、シートに保護がかけられること

現在の時刻を取得するNow関数について

Now関数を使うことで、システムの現在時刻を取得することができます。

構文
Now()

シートに保護をかけるには

記録されたセルは、編集されることを防ぐために、このシートにはパスワード付きの保護をかけるよう設計します。

ActiveSheet.Protect Password:="1234"

これにより、アクティブなシートにパスワード「1234」の保護がかかります。
このプログラムの最後で、このProtectメソッドで保護をかければ、一般ユーザーはセルの編集ができなくなります。

ただし、保護がかかっていると、マクロを使ってもセルの値を変更できなくなります。

つまり、このRecordNumber関数では、

  1. シートの保護を解除
  2. セルに時刻と乱数を記録
  3. シートに保護をかける

このような流れになります。

ちなみに、保護の解除は次のとおりです。

ActiveSheet.Unprotect Password:="1234"