MathRand()是如何生成数值的? - 页 3 1234 新评论 Forester 2020.04.24 17:42 #21 我把MathRandomUniform 添加到我的脚本,以便进行比较。,我把点的生成设置为1000000。为了估计分布,我把所有1000000个点显示在屏幕上,作为一个1000*1000的正方形。你击中一个点的次数越多,其颜色就越亮。 我 设置了1000万次RNG的重复,所以平均每个点应该被击中10次。 以下是结果。 RND。 我的RandomInteger的变体。 关于MathRand()。 在 MathRandomUniform()。 前两个RND是相当均匀的,3和4有空隙,即不均匀。 跳过的原因是MathRand分辨率=32767。 在乘数为1000000时,我们将得到跳过1000000/32767=30分。MathRandomUniform 在 图像上是相似的,可能,它有同样的30个 跳 过 。 另一种变体。让我们把最大的数字设定为30000。 RND和 RandomInteger是相等的,就像它们是一百万 一样。MathRand和 MathRandomUniform 看起来像这样(有放大的块)。 没有空隙(黑点到位置30000)。但有些明显更亮。这是对30000/32767的不均匀取舍。每第11个点得到两倍的命中率。 统一的东西可以从 MathRand在最大3000的时候得到...4000.下面是3500的放大变体: 前两种变体在接近最大数字时,对于RandomInteger(其 分辨率 约为10亿)为1 亿,对于RND为40亿分辨率为4亿,-也会由于四舍五入而开始不均匀地分布。 我已经附上了文件,你可以重复这个实验。 我决定为自己使用自己的函数,它比RND慢25%,但更紧凑和清晰。 我可以将分辨率提高到32767倍以上,见博客 中的代码。 请注意。 文章中的RND开发者指出 在种子=0时,该函数随机地改变初始值。 在每次重启时,我都设置种子=0,但有分布的图片在重启时没有变化。也就是说,这个说法是不正确的。从代码中你也看不出为什么它应该变成随机的。因此,为了随机初始化,必须将种子设置为一个随机数,例如seed=GetTickCount()。 对于RandomInteger()函数,我们看到重新启动时的点的重新分配。如果设置了srand(0);,分布也会在重新启动时开始重复。所以为了让这个函数随机初始化,我需要不调用srand,或者使用MathSrand(GetTickCount()) 和时间戳。 附加的文件: RandGenerator.mq5 9 kb Rorschach 2020.04.24 19:49 #22 请记住,xor128通过了特殊的随机性测试,并且与标准的rand可以 关于交易、自动交易系统和策略测试的论坛 交易中的机器学习:理论、实践、交易及其他 Rorschach, 2020.04.19 22:18 我是个杂工,我把RSCH弄坏了((() #include <Canvas\Canvas.mqh> void OnStart() {CCanvas C; int h=1024; int w=2048; C.CreateBitmapLabel("11",100,100,w,h); for(int y=0;y<h;y++) {//srand(GetMicrosecondCount()); for(int x=0;x<w;x++) {uchar c=0; for(int k=0;k<16;k++) {c=uchar(255.*rand()/32767.); } C.PixelSet(x,y,ARGB(255,c,c,c)); } } C.Update(); 1种方法:W必须是2的幂,K是4的倍数 方法2:取消对srand的注释 方法2也应该对梅尔森漩涡起作用 Forester 2020.04.24 20:15 #23 Rorschach: 请注意,xor128通过了特殊的随机性测试,用一个标准的rand就可以 你显示每16个兰特调用。这种周期性的某种模式显现出来。 我正在使用所有连续的呼叫,每一个都是2个。从视觉上看,从我的照片上看,我没有看到与xor128的1000万次重复有任何区别。 Forester 2020.04.24 21:25 #24 Rorschach: 请注意,xor128通过了特殊的随机性测试,用一个标准的rand就可以 我试着把我自己的函数和xor128替换成你的函数 #include <Canvas\Canvas.mqh> void OnStart() {CCanvas C; RND rn; rn.SRand(0); int h=1024; int w=2048; C.CreateBitmapLabel("11",100,100,w,h); for(int y=0;y<h;y++) {//srand(GetMicrosecondCount()); rn.SRand(GetMicrosecondCount()); for(int x=0;x<w;x++) {uchar c=0; for(int k=0;k<16;k++) //{c=uchar(255.*rand()/32767.);} //{c=uchar(255.*RandomInteger(1073741824)/1073741824.0); } {c=(uchar)(255.0*rn.Rand_01()); } C.PixelSet(x,y,ARGB(255,c,c,c)); } } C.Update(); } int RandomInteger(int max_vl){return (int)MathFloor((MathRand()+MathRand()*32767.0)/1073741824.0*max_vl);}//случайное Int от 0 до 1073741824//если из define переместить в код RNDUint, то скорость работы увеличится на 30% для 10 млн повторов с 600 мс до 850 мс. Это почти как RandomInteger()#define xor32 xx=xx^(xx<<13);xx=xx^(xx>>17);xx=xx^(xx<<5)#define xor128 t=(x^(x<<11));x=y;y=z;z=w;w=(w^(w>>19))^(t^(t>>8))#define inidat x=123456789;y=362436069;z=521288629;w=88675123;xx=2463534242 class RND{ protected: uint x,y,z,w,xx,t; public: RND(void){inidat;}; ~RND(void){}; uint RandMaxUI(uint max_v) {xor128;return((uint)MathFloor((double)w/UINT_MAX*max_v));};//равномерное распределение на отрезке [0,max_v]. uint int RandMaxI(int max_v) {xor128;return((int) MathFloor((double)w/UINT_MAX*max_v));};//равномерное распределение на отрезке [0,max_v]. int uint Rand() {xor128;return(w);};//равномерное распределение на отрезке [0,UINT_MAX=4294967295]. double Rand_01() {xor128;return((double)w/UINT_MAX);};//равномерное распределение на отрезке [0,1]. void Reset() {inidat;};//сброс всех исходных значений в первоначальное состояние. void SRand(uint seed) {//установка новых исходных значений генератора.seed= [0,UINT_MAX=4294967295]. При seed=0 функция меняет начальные значения случайным образом. int i;if(seed!=0){xx=seed;}for(i=0;i<16;i++){xor32;}xor32;x=xx;xor32;y=xx;xor32;z=xx;xor32;w=xx;for(i=0;i<16;i++){xor128;} };}; RandomInteger()也有一些除法。 用xor128更好,但有一些带状现象。 我不确定在正常使用中(不是16个中的1个)这些来自RandomInteger()的破折号会有什么影响...而且也不清楚他们的意思... 但我认为xor128更可靠。 How does MathRand() generate 统计估计 A new VPS needed Rashid Umarov 2020.04.25 07:09 #25 Rorschach: 请注意,xor128通过了特殊的随机性测试,用一个标准的rand就可以 你有Mersen的代码吗?我曾在OpenCL的某个地方做过,但还没来得及把它移植到MQL5。比较一下会很有意思。 方法2也应适用于梅尔森的漩涡 Rorschach 2020.04.25 14:15 #26 Rashid Umarov: 你有Mersen的代码吗?我曾在OpenCL的某个地方做过,但还没来得及把它移植到MQL5。比较一下会很有意思。 在这里,我自己还没有使用过它。 Rorschach 2020.04.25 14:21 #27 elibrarius: 你显示的是每16次呼叫兰特。这种周期性的某种模式显现出来。 我正在使用所有连续的呼叫,每一个都是2个。 从视觉上看,从我的照片上看,我没有看到与xor128的1000万次重复有任何区别。 我不知道你的使用目的是什么,只是提醒你,可能会有意外的收获。 Rashid Umarov 2020.04.25 14:56 #28 Rorschach: 在这里,我自己还没有使用过它。 谢谢!结果是代码比OpenCL上的要大。我将在某个时候尝试弄清楚。 Maxim Kuznetsov 2020.04.25 15:18 #29 对ter.ver的友好打击,整数的魔力,四舍五入,模块运算和双倍的技巧 :-) 如果f(x):: 在(0;N)上均匀分布 的整数,并不意味着g(x)=N/(double)f(x)会在(0;1)上均匀分布,也会通过所有测试。 关于g(x)=f(x)mod M也是如此,但N mod M=0是个罕见的例外。 PS/顺便说一句,g(x)=f(x)/(double)N也不会是均匀的。将会有分裂的焦点。也就是说,图中会出现摩尔纹。 PPS/对于随机性的视觉 "测试",除了模数钝方之外,还应用了 "乌拉姆蜗牛 "的变种。 Forester 2020.04.26 07:00 #30 Rorschach: 在这里,我自己还没有使用过它。 从这个代码中测量了CRandomMersenne和CRandomMother的性能。它们的速度比xor128慢3倍。这不是很令人满意。但根据你的代码,在你打破GSF的地方,它们看起来比xor128(没有竖条)更好。 1234 新评论 您错过了交易机会: 免费交易应用程序 8,000+信号可供复制 探索金融市场的经济新闻 注册 登录 拉丁字符(不带空格) 密码将被发送至该邮箱 发生错误 使用 Google 登录 您同意网站政策和使用条款 如果您没有帐号,请注册 可以使用cookies登录MQL5.com网站。 请在您的浏览器中启用必要的设置,否则您将无法登录。 忘记您的登录名/密码? 使用 Google 登录
我把MathRandomUniform 添加到我的脚本,以便进行比较。
,我把点的生成设置为1000000。为了估计分布,我把所有1000000个点显示在屏幕上,作为一个1000*1000的正方形。你击中一个点的次数越多,其颜色就越亮。
我 设置了1000万次RNG的重复,所以平均每个点应该被击中10次。
以下是结果。
![](https://c.mql5.com/3/317/m1__1.png)
RND。
我的RandomInteger的变体。
关于MathRand()。
在 MathRandomUniform()。
前两个RND是相当均匀的,3和4有空隙,即不均匀。
跳过的原因是MathRand分辨率=32767。 在乘数为1000000时,我们将得到跳过1000000/32767=30分。MathRandomUniform 在 图像上是相似的,可能,它有同样的30个 跳 过 。
另一种变体。让我们把最大的数字设定为30000。 RND和 RandomInteger是相等的,就像它们是一百万 一样。MathRand和 MathRandomUniform 看起来像这样(有放大的块)。
没有空隙(黑点到位置30000)。但有些明显更亮。这是对30000/32767的不均匀取舍。每第11个点得到两倍的命中率。
统一的东西可以从 MathRand在最大3000的时候得到...4000.下面是3500的放大变体:
前两种变体在接近最大数字时,对于RandomInteger(其 分辨率 约为10亿)为1 亿,对于RND为40亿分辨率为4亿,-也会由于四舍五入而开始不均匀地分布。
我已经附上了文件,你可以重复这个实验。
我决定为自己使用自己的函数,它比RND慢25%,但更紧凑和清晰。 我可以将分辨率提高到32767倍以上,见博客 中的代码。
请注意。
文章中的RND开发者指出
在每次重启时,我都设置种子=0,但有分布的图片在重启时没有变化。也就是说,这个说法是不正确的。从代码中你也看不出为什么它应该变成随机的。因此,为了随机初始化,必须将种子设置为一个随机数,例如seed=GetTickCount()。
对于RandomInteger()函数,我们看到重新启动时的点的重新分配。如果设置了srand(0);,分布也会在重新启动时开始重复。所以为了让这个函数随机初始化,我需要不调用srand,或者使用MathSrand(GetTickCount()) 和时间戳。
请记住,xor128通过了特殊的随机性测试,并且与标准的rand可以
关于交易、自动交易系统和策略测试的论坛
交易中的机器学习:理论、实践、交易及其他
Rorschach, 2020.04.19 22:18
我是个杂工,我把RSCH弄坏了((()
1种方法:W必须是2的幂,K是4的倍数
方法2:取消对srand的注释
方法2也应该对梅尔森漩涡起作用请注意,xor128通过了特殊的随机性测试,用一个标准的rand就可以
你显示每16个兰特调用。这种周期性的某种模式显现出来。
我正在使用所有连续的呼叫,每一个都是2个。从视觉上看,从我的照片上看,我没有看到与xor128的1000万次重复有任何区别。
请注意,xor128通过了特殊的随机性测试,用一个标准的rand就可以
我试着把我自己的函数和xor128替换成你的函数
void OnStart()
{CCanvas C;
RND rn; rn.SRand(0);
int h=1024;
int w=2048;
C.CreateBitmapLabel("11",100,100,w,h);
for(int y=0;y<h;y++)
{//srand(GetMicrosecondCount());
rn.SRand(GetMicrosecondCount());
for(int x=0;x<w;x++)
{uchar c=0;
for(int k=0;k<16;k++)
//{c=uchar(255.*rand()/32767.);}
//{c=uchar(255.*RandomInteger(1073741824)/1073741824.0); }
{c=(uchar)(255.0*rn.Rand_01()); }
C.PixelSet(x,y,ARGB(255,c,c,c));
}
}
C.Update();
}
int RandomInteger(int max_vl){return (int)MathFloor((MathRand()+MathRand()*32767.0)/1073741824.0*max_vl);}//случайное Int от 0 до 1073741824
//если из define переместить в код RNDUint, то скорость работы увеличится на 30% для 10 млн повторов с 600 мс до 850 мс. Это почти как RandomInteger()
#define xor32 xx=xx^(xx<<13);xx=xx^(xx>>17);xx=xx^(xx<<5)
#define xor128 t=(x^(x<<11));x=y;y=z;z=w;w=(w^(w>>19))^(t^(t>>8))
#define inidat x=123456789;y=362436069;z=521288629;w=88675123;xx=2463534242
class RND{
protected:
uint x,y,z,w,xx,t;
public:
RND(void){inidat;};
~RND(void){};
uint RandMaxUI(uint max_v) {xor128;return((uint)MathFloor((double)w/UINT_MAX*max_v));};//равномерное распределение на отрезке [0,max_v]. uint
int RandMaxI(int max_v) {xor128;return((int) MathFloor((double)w/UINT_MAX*max_v));};//равномерное распределение на отрезке [0,max_v]. int
uint Rand() {xor128;return(w);};//равномерное распределение на отрезке [0,UINT_MAX=4294967295].
double Rand_01() {xor128;return((double)w/UINT_MAX);};//равномерное распределение на отрезке [0,1].
void Reset() {inidat;};//сброс всех исходных значений в первоначальное состояние.
void SRand(uint seed) {//установка новых исходных значений генератора.seed= [0,UINT_MAX=4294967295]. При seed=0 функция меняет начальные значения случайным образом.
int i;if(seed!=0){xx=seed;}for(i=0;i<16;i++){xor32;}xor32;x=xx;xor32;y=xx;xor32;z=xx;xor32;w=xx;for(i=0;i<16;i++){xor128;}
};
};
RandomInteger()也有一些除法。
![](https://c.mql5.com/3/317/Untitled-1.png)
用xor128更好,但有一些带状现象。
我不确定在正常使用中(不是16个中的1个)这些来自RandomInteger()的破折号会有什么影响...而且也不清楚他们的意思...
但我认为xor128更可靠。
请注意,xor128通过了特殊的随机性测试,用一个标准的rand就可以
你有Mersen的代码吗?我曾在OpenCL的某个地方做过,但还没来得及把它移植到MQL5。比较一下会很有意思。
你有Mersen的代码吗?我曾在OpenCL的某个地方做过,但还没来得及把它移植到MQL5。比较一下会很有意思。
在这里,我自己还没有使用过它。
你显示的是每16次呼叫兰特。这种周期性的某种模式显现出来。
我正在使用所有连续的呼叫,每一个都是2个。 从视觉上看,从我的照片上看,我没有看到与xor128的1000万次重复有任何区别。
我不知道你的使用目的是什么,只是提醒你,可能会有意外的收获。
在这里,我自己还没有使用过它。
谢谢!结果是代码比OpenCL上的要大。我将在某个时候尝试弄清楚。
对ter.ver的友好打击,整数的魔力,四舍五入,模块运算和双倍的技巧 :-)
如果f(x):: 在(0;N)上均匀分布 的整数,并不意味着g(x)=N/(double)f(x)会在(0;1)上均匀分布,也会通过所有测试。
关于g(x)=f(x)mod M也是如此,但N mod M=0是个罕见的例外。
PS/顺便说一句,g(x)=f(x)/(double)N也不会是均匀的。将会有分裂的焦点。也就是说,图中会出现摩尔纹。
PPS/对于随机性的视觉 "测试",除了模数钝方之外,还应用了 "乌拉姆蜗牛 "的变种。
在这里,我自己还没有使用过它。
从这个代码中测量了CRandomMersenne和CRandomMother的性能。它们的速度比xor128慢3倍。这不是很令人满意。但根据你的代码,在你打破GSF的地方,它们看起来比xor128(没有竖条)更好。