frannor.c
来自「该程序是用vc开发的对动态数组进行管理的DLL」· C语言 代码 · 共 170 行
C
170 行
/* Copyright (c) Colorado School of Mines, 2003.*//* All rights reserved. *//*********************** self documentation **********************//*****************************************************************************FRANNOR - functions to generate a pseudo-random float normally distributed with N(0,1); i.e., with zero mean and unit variance.frannor return a normally distributed random floatsrannor seed random number generator for normal distribution******************************************************************************Function Prototypes:float frannor (void);void srannor (int seed);******************************************************************************frannor:Input: (none)Returned: normally distributed random floatsrannor:Input:seed different seeds yield different sequences of random numbers.******************************************************************************Notes:Adapted from subroutine rnor in Kahaner, Moler and Nash (1988)which in turn was based on an algorithm by Marsaglia and Tsang (1984).******************************************************************************References:"Numerical Methods and Software", D.Kahaner, C. Moler, S. Nash, Prentice Hall, 1988.Marsaglia G. and Tsang, W. W., 1984,A fast, easily implemented method for sampling from decreasing or symmetricunimodal density functions: SIAM J. Sci. Stat. Comput., v. 5, no. 2,p. 349-359.*****************************************************************************Author: Dave Hale, Colorado School of Mines, 01/21/89*****************************************************************************//**************** end self doc ********************************/#include "cwp.h"/* constants for normal random number generator */#define AA 12.37586F#define B 0.4878992F#define C 12.67706F#define C1 0.9689279F#define C2 1.301198F#define PC 0.01958303F#define XN 2.776994F#define OXN 0.3601016F#define NBITS 24static float v[]={ 0.3409450f, 0.4573146f, 0.5397793f, 0.6062427f, 0.6631691f, 0.7136975f, 0.7596125f, 0.8020356f, 0.8417227f, 0.8792102f, 0.9148948f, 0.9490791f, 0.9820005f, 1.0138492f, 1.0447810f, 1.0749254f, 1.1043917f, 1.1332738f, 1.1616530f, 1.1896010f, 1.2171815f, 1.2444516f, 1.2714635f, 1.2982650f, 1.3249008f, 1.3514125f, 1.3778399f, 1.4042211f, 1.4305929f, 1.4569915f, 1.4834526f, 1.5100121f, 1.5367061f, 1.5635712f, 1.5906454f, 1.6179680f, 1.6455802f, 1.6735255f, 1.7018503f, 1.7306045f, 1.7598422f, 1.7896223f, 1.8200099f, 1.8510770f, 1.8829044f, 1.9155830f, 1.9492166f, 1.9839239f, 2.0198430f, 2.0571356f, 2.0959930f, 2.1366450f, 2.1793713f, 2.2245175f, 2.2725185f, 2.3239338f, 2.3795007f, 2.4402218f, 2.5075117f, 2.5834658f, 2.6713916f, 2.7769943f, 2.7769943f, 2.7769943f, 2.7769943f};/* internal state variables for uniform random number generator */static int i=16,j=4;static float u[]={ 0.8668672834288f, 0.3697986366357f, 0.8008968294805f, 0.4173889774680f, 0.8254561579836f, 0.9640965269077f, 0.4508667414265f, 0.6451309529668f, 0.1645456024730f, 0.2787901807898f, 0.06761531340295f, 0.9663226330820f, 0.01963343943798f, 0.02947398211399f, 0.1636231515294f, 0.3976343250467f, 0.2631008574685f};/* macro to generate a random number uni uniform on [0,1) */#define UNI(uni) \ uni = u[i]-u[j]; if (uni<0.0) uni += 1.0; u[i] = uni; \ if (--i<0) i = 16; if (--j<0) j = 16floatfrannor(void)/**************************************************************************return a normally distributed random float***************************************************************************Returned: normally distributed random float**************************************************************************/{ int k; float uni,vni,rnor,x,y,s,bmbx,xnmx; /* uni is uniform on [0,1) */ UNI(uni); /* vni is uniform on [-1,1) */ vni = uni+uni-1.0F; /* k is in range [0,63] */ k = ((int)(u[i]*128))%64; /* fast part */ rnor = vni*v[k+1]; if (ABS(rnor)<=v[k]) return rnor; /* slow part */ x = (ABS(rnor)-v[k])/(v[k+1]-v[k]); UNI(y); s = x+y; if (s<=C2) { if (s<=C1) return rnor; bmbx = B-B*x; if (y<=C-AA*exp(-0.5*bmbx*bmbx)) { if (exp(-0.5*v[k+1]*v[k+1])+y*PC/v[k+1] <= exp(-0.5*rnor*rnor)) return rnor; do { UNI(y); x = (float)(OXN*log(y)); UNI(y); } while (-2.0*log(y)<=x*x); xnmx = XN-x; return (rnor>=0.0 ? ABS(xnmx) : -ABS(xnmx)); } } bmbx = B-B*x; return (rnor>=0.0 ? ABS(bmbx) : -ABS(bmbx));} voidsrannor (int seed)/*****************************************************************************seed random number generator******************************************************************************Input:seed different seeds yield different sequences of random numbers.*****************************************************************************/{ int ii,jj,ia,ib,ic,id; float s,t; i = 16; j = 4; ia=ABS(seed)%32707; ib=1111; ic=1947; for (ii=0; ii<17; ii++) { s = 0.0; t = 0.5; for (jj=0; jj<64; jj++) { id = ic-ia; if (id<0) { id += 32707; s += t; } ia = ib; ib = ic; ic = id; t *= 0.5; } u[ii] = s; }}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?