相关疑难解决方法(0)

由于 Mersenne Twister 引擎上的负索引,libstdc++ std::random 上的未定义行为(根据 clang -fsanitize=integer)

我在 Ubuntu 20.04 LTS 上使用 clang++ 10,-fsanitize-undefined-trap-on-error -fsanitize=address,undefined,nullability,implicit-integer-truncation,implicit-integer-arithmetic-value-change,implicit-conversion,integer

我的代码正在生成随机字节

    std::random_device rd;
    std::mt19937 gen(rd());
    std::uniform_int_distribution<uint8_t> dd(0, 255);
    ...
    ch = uint8_t(dd(gen));
Run Code Online (Sandbox Code Playgroud)

最后一行导致消毒程序报告未定义的行为位于bits/random.tcc中

template<...> void  mersenne_twister_engine<...>::
    _M_gen_rand(void)   {
      const _UIntType __upper_mask = (~_UIntType()) << __r;
      const _UIntType __lower_mask = ~__upper_mask;

      for (size_t __k = 0; __k < (__n - __m); ++__k)
      {
         _UIntType __y = ((_M_x[__k] & __upper_mask)
               | (_M_x[__k + 1] & __lower_mask));
         _M_x[__k] = (_M_x[__k + __m] ^ (__y >> 1)
               ^ ((__y & 0x01) ? __a : 0)); …
Run Code Online (Sandbox Code Playgroud)

c++ g++ clang sanitizer libstdc++

25
推荐指数
3
解决办法
4165
查看次数

c ++ 11 STL的binomial_distribution非常慢

我使用STL的'随机'生成二项分布的随机数.当范围很大时,它变得非常慢.对于范围40,生成100个数字需要12秒.对于更大的范围,时间会急剧增加(我需要大约10000的范围).它似乎不依赖于概率参数.我正在使用g ++ 4.5.0.

#include <iostream>
#include <random>

using namespace std;

vector<int> v;

default_random_engine gen(123);
binomial_distribution<int> rbin(40,0.7);

int main(){
  v.reserve(2000);
  for(int i=0; i<100;++i){
    v.push_back(rbin(gen));
   }
}
Run Code Online (Sandbox Code Playgroud)

输出:

50.~/.../fs/> g++ -std=c++0x q.cpp 
51.~/.../fs/> time ./a.out 
real    0m12.102s
user    0m12.094s
sys     0m0.002s
52.~/.../fs/>
Run Code Online (Sandbox Code Playgroud)

我可以使用正态近似,但它对于概率参数的极值是不好的.

更新:

'-O3'选项时间变为~2秒.使用g ++ 4.6.3时,问题完全消失了 - 几乎没有时间依赖于范围,100个数字的生成需要5ms.

c++ random gcc libstdc++ c++11

5
推荐指数
1
解决办法
525
查看次数

标签 统计

c++ ×2

libstdc++ ×2

c++11 ×1

clang ×1

g++ ×1

gcc ×1

random ×1

sanitizer ×1