[C++] Windows 환경에서 random_device를 사용할 때, 매번 실행할 때마다 같은 무작위 수열을 생성하는 문제

4933 단어 RandomWindowsC++

환경

  • Windows 10
  • Git Bash
  • $ bash --version
    GNU bash, version 4.3.42(5)-release (x86_64-pc-msys)
    Copyright (C) 2013 Free Software Foundation, Inc.
    License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
    
    This is free software; you are free to change and redistribute it.
    There is NO WARRANTY, to the extent permitted by law.
    
    
    ※ 댓글을 받았기 때문에 기억하기
    이번 문제는 Windows가 좋지 않은 것이 아니라mingw의libstdc++ 설치입니다
    (자세한 내용은 설명 표시줄 참조)

    문제


    어느 날, 아래 절차와 C++ 코드를 통해 [0,2π]의 균등한 랜덤 수를 생성하려고 시도했다
  • std::random_device 비확정적 랜덤 생성
  • mt19937의 초기 씨앗에 random_device 에서 생성된 값
  • 추가
  • 실행할 때마다 다른 랜덤 수 생성
  •     // この乱数生成器が実行毎に別の乱数を生成するかは環境依存である
        // Windows環境では実行毎に同じ値を出すので注意
        // Ubuntuでは実行毎に別の乱数を生成した
        std::random_device rnd;
        std::mt19937 mt(rnd());
    
        std::uniform_real_distribution<double> theta(0.0, 2*M_PI);
        for(int i = 0; i < 10; i++) std::cout << theta(mt) << std::endl;
    
    아래와 같이 번역하다g++ kadai3.cpp -o kadai3 -std=gnu++11한번 실행해 보았더니 결과는 다음과 같다

    매번 실행할 때마다 같은 랜덤 수가 돌아오잖아!

    원인


    이상하다고 생각해서 찾아봤는데 아래 페이지에
    https://cpprefjp.github.io/reference/random/random_device.html
    Windows 버전 GCC(MinGW,libstdc++)에서 random_장치 클래스는 위조 랜덤 생성기 mt19937에서 실현됩니다.이 환경의 기본값은 고정된 무작위 열을 생성합니다.구조 함수의 매개 변수로서 피드 값을 문자열화하고 전달하면 mt19937의 피드로 간주되지만 비결정적인 무작위 수로 처리되지 않습니다.이 환경에서 random_장치 사용을 권장하지 않음
    로 바꾸기
  • 플랫폼 간
  • CPU에서 제공하는 RDRAND, RDSEED 명령
  • Windows
  • rand_s(CryptGenRandom 패키지)
  • RtlGenRandom 함수(CryptGenRandom 대체 권장)
  • CryptGenRandom 함수
  • (자세한 내용은 링크 주소 참조)
    즉, Windows 환경random_device에서 비결정적 랜덤으로 실행되지 않기 때문에 상기 코드로'매번 실행되는 다른 랜덤 수열'을 생성할 수 없습니다

    검증


    명령 프롬프트에서 실행


    명령 프롬프트의 g++(버전은 아래와 같음)에서 컴파일하고 실행할 때 결과가 같습니다 (실행 결과가 같기 때문에 생략됨)
    >g++ --version
    g++ (tdm64-1) 5.1.0
    Copyright (C) 2015 Free Software Foundation, Inc.
    This is free software; see the source for copying conditions.  There is NO
    warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
    

    가상 박스의 Ubuntu에서 실행


    동일한 Windows 환경에서 VirtualBox를 시작하고 Ubuntu16.04에서 실행할 때
    $ g++ --version
    g++ (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
    Copyright (C) 2015 Free Software Foundation, Inc.
    This is free software; see the source for copying conditions.  There is NO
    warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
    

    실행할 때마다 다른 무작위 수열을 만들어서 해결합니다.
    안에 목적 페이지를 찾지 못하는 데 시간이 오래 걸렸어요. 누구를 도와줄 수 있다면 기쁠 거예요.

    좋은 웹페이지 즐겨찾기