正規乱数(ガウス乱数)を生成する †正規乱数とは、生成結果が正規分布に従うような乱数である。(対義語は一様乱数) C++言語による正規乱数の生成 †gaussianRand.cpp #include <stdio.h> // 標準入出力 //
#include <stdlib.h> // 標準ライブラリ //
#include <math.h> // 数理ライブラリ //
#include <time.h> // 時間計測のため //
// //
const double PI = 3.14159265358979; // 円周率 //
// //
double gaussianRand( double vd_stdev, double vd_meanValue ); // 正規乱数発生関数 //
// //
/* Rand Test **************************************************//* 正規乱数発生ドライバ */
int main( void ) // //
{ // //
clock_t start, end; // 時間計測用 //
unsigned int cnt; // ループカウンタ //
double randNum = 0.0; // 乱数取得用 //
// //
start = clock(); // 時間計測スタート //
srand( (unsigned int)time( NULL ) ); // 乱数の種を設定 //
// //
for( ; ; ) // 無限ループ //
{ // //
for( cnt = 0; cnt < 10; cnt++ ) // 何回か発生させて表示する //
{ // //
randNum = gaussianRand( 1.0, 0.0 ); // 正規乱数の取得 //
printf( "%02d: %f\n", cnt, randNum ); // 画面表示 //
} // //
// //
end = clock(); // 時間計測ストップ //
printf( "%d msかかりました\n", end-start ); // 画面表示 //
// //
break; // 処理終了 //
} // //
// //
return( 0 ); // 処理終了 //
} // //
//*Rand Test **************************************************//* 正規乱数発生ドライバ */
/* Gaussian Rand **********************************************//* 正規乱数発生処理 */
double gaussianRand( double vd_stdev, // 引数01: 標準偏差 //
double vd_meanValue ) // 引数02: 平均値 //
{ // //
double rtnNum = 0.0; // リターン用 //
static int sw = 0; // リターンの切替用 //
// //
double randNum_1; // 乱数その1 //
double randNum_2; // 乱数その2 //
double whiteGaussianNoise_1; // ホワイトガウスノイズその1 //
static double whiteGaussianNoise_2; // ホワイトガウスノイズその2 //
// //
if( sw == 0 ) // スイッチが0か //
{ // スイッチが0なら //
sw = 1; // スイッチ切替え //
randNum_1 = ((double)rand()) / RAND_MAX; // (0,9]の乱数取得 //
randNum_2 = ((double)rand()) / RAND_MAX; // (0,9]の乱数取得 //
// //
whiteGaussianNoise_1 = vd_stdev * sqrt( -2.0 * log( randNum_1 ) ) * // 正規乱数1 //
cos( 2.0 * PI * randNum_2 ) + vd_meanValue; // //
whiteGaussianNoise_2 = vd_stdev * sqrt( -2.0 * log( randNum_1 ) ) * // 正規乱数2 //
sin( 2.0 * PI * randNum_2 ) + vd_meanValue; // //
// //
rtnNum = whiteGaussianNoise_1; // リターンに正規乱数1を設定 //
} // //
else // スイッチが0以外の場合 //
{ // //
sw = 0; // スイッチ切替え //
// //
rtnNum = whiteGaussianNoise_2; // リターンに正規乱数2を設定 //
} // //
// //
return( rtnNum ); // 生成した正規乱数を返して終了 //
} // //
//*Gaussian Rand **********************************************//* 正規乱数発生処理 */
表示結果: †>gaussianRand.exe 00: 0.977696 01: 1.646302 02: 2.349632 03: 0.509217 04: 1.080539 05: -0.208485 06: -1.016973 07: -0.839387 08: 0.177065 09: 0.619993 8 msかかりました 修正履歴 †課題 †
これ、1個目と2個目の平均と標準偏差が違う場合に問題がある。 標準正規乱数でとっておいて2を出力する際に平均を足して標準偏差をかける方がいい。 参考ページ † |