100 lines
2.0 KiB
Plaintext
100 lines
2.0 KiB
Plaintext
// Copyright (C) 2010, Guy Barrand. All rights reserved.
|
|
// See the file tools.license for terms.
|
|
|
|
#ifndef tools_randf
|
|
#define tools_randf
|
|
|
|
#include <cstdlib> //::rand, RAND_MAX
|
|
#include "fmath"
|
|
|
|
namespace tools {
|
|
namespace randf {
|
|
|
|
class flat {
|
|
public:
|
|
float shoot() const {
|
|
// Shoot random numbers in [0,1] according a flat distribution.
|
|
float value = (float)::rand();
|
|
value /= (float)RAND_MAX;
|
|
return value;
|
|
}
|
|
};
|
|
|
|
class gauss {
|
|
public:
|
|
gauss(float a_mean = 0,float a_std_dev = 1)
|
|
:m_mean(a_mean),m_std_dev(a_std_dev){}
|
|
public:
|
|
gauss(const gauss& a_from)
|
|
:m_mean(a_from.m_mean),m_std_dev(a_from.m_std_dev){}
|
|
gauss& operator=(const gauss& a_from) {
|
|
m_mean = a_from.m_mean;
|
|
m_std_dev = a_from.m_std_dev;
|
|
return *this;
|
|
}
|
|
public:
|
|
float shoot() const {
|
|
// Shoot random numbers according a
|
|
// gaussian distribution of mean 0 and sigma 1.
|
|
float v1,v2,r,fac;
|
|
do {
|
|
v1 = 2 * m_flat.shoot() - 1;
|
|
v2 = 2 * m_flat.shoot() - 1;
|
|
r = v1*v1 + v2*v2;
|
|
} while ( r > 1 );
|
|
fac = fsqrt(-2*flog(r)/r);
|
|
return (v2 * fac) * m_std_dev + m_mean;
|
|
}
|
|
protected:
|
|
flat m_flat;
|
|
float m_mean;
|
|
float m_std_dev;
|
|
};
|
|
|
|
class bw {
|
|
public:
|
|
bw(float a_mean = 0,float a_gamma = 1)
|
|
:m_mean(a_mean),m_gamma(a_gamma){}
|
|
public:
|
|
bw(const bw& a_from)
|
|
:m_mean(a_from.m_mean),m_gamma(a_from.m_gamma){}
|
|
bw& operator=(const bw& a_from) {
|
|
m_mean = a_from.m_mean;
|
|
m_gamma = a_from.m_gamma;
|
|
return *this;
|
|
}
|
|
public:
|
|
float shoot() const {
|
|
float rval = 2 * m_flat.shoot() - 1;
|
|
float displ = 0.5f * m_gamma * ftan(rval * fhalf_pi());
|
|
return m_mean + displ;
|
|
}
|
|
protected:
|
|
flat m_flat;
|
|
float m_mean;
|
|
float m_gamma;
|
|
};
|
|
|
|
class exp {
|
|
public:
|
|
exp(float a_rate = 1):m_rate(a_rate){}
|
|
public:
|
|
exp(const exp& a_from):m_rate(a_from.m_rate){}
|
|
exp& operator=(const exp& a_from) {m_rate = a_from.m_rate;return *this;}
|
|
public:
|
|
float shoot() const {
|
|
float v;
|
|
do {
|
|
v = m_flat.shoot();
|
|
} while(v<=0);
|
|
return -flog(v)/m_rate;
|
|
}
|
|
protected:
|
|
flat m_flat;
|
|
float m_rate;
|
|
};
|
|
|
|
}}
|
|
|
|
#endif
|