C/C++ 랜덤 난수 rand() 사용법 및 다양한 구현 방식

2024. 12. 12. 18:00·프로그래밍/C++
목차
  1. 1. rand() 함수 : 난수 생성
  2. 2. rand() 사용법
  3. 🟦 최소, 최대 범위 지정해서 생성하기
  4. 🟦 난수 생성 범위 제한
  5. 3. C++ random 라이브러리로 난수 생성
어두운 배경이 싫으시다면 페이지 우측 하단에 보이는 초승달 모양의 아이콘을 클릭하면 화이트모드로 변경됩니다.
초승달 모양 버튼 : 화이트/다크 모드 전환
테마모드 변경 가이드

 

1. rand() 함수 : 난수 생성

기존의 C 스타일의 rand() 함수는 <cstdlib> 헤더에서 제공하고 있는 난수 함수입니다. C++ 에서는 <iostream> 안에 기본적으로 포함되기 때문에 해당 라이브러리를 추가하면 사용 가능합니다.

 

rand() 함수로 난수를 발생하게 되면 0 ~ RAND_MAX 라는 범위 안에서 난수가 생성됩니다. 이때 RAND_MAX는 상수로 32,767로 정의되어 있습니다. 그래서 최종적으로 발생되는 난수는 0 ~ 32,767 이라고 보면 됩니다.

 

rand() 함수는 가장 기본적인 형태의 의사난수(pseudo-random number) 발생 함수이기 때문에 간단한 작업에 사용하기에는 적합하지만, 난수 품질이나 보안성이 낮아서 복잡한 난수 발생이나 멀티스레드 등에서 사용하기에는 적합하지 않습니다.

 

rand() 함수는 난수를 발생할 때 시드값(seed)을 사용하는데, 같은 시드값이라면 항상 같은 결과를 반환합니다. 그래서 다양한 결과를 얻고 싶다면 srand() 함수를 이용하여 시드를 초기화해야 합니다. 보통은 현재 시간을 시드로 사용합니다.

 

🔹난수 생성 코드 예제

cpp
닫기
#include <iostream>
using namespace std;
int main()
{
srand((unsigned int)time(NULL)); // 난수 seed 초기화
for (int i = 0; i < 10; ++i) {
cout << rand() << endl; // 0 ~ 32,767 범위에서 랜덤 난수 생성
}
return 0;
}

 

2. rand() 사용법

🟦 최소, 최대 범위 지정해서 생성하기

특정한 범위의 값으로 난수를 발생하고 싶다면 나머지 연산자 %를 사용하여 최대값 범위로 연산하면 됩니다. 다만 난수로 생성되는 최대값의 범위는 지정한 값보다 1이 작은 값이 생성됩니다.

 

ex) rand() % 50 => 0 ~ 49 범위에서 난수 발생

 

최솟값을 지정하고 싶다면 단순히 더해주면 됩니다.

ex) (rand() % 50) + 1 => 1 ~ 50 범위에서 난수 발생

 

만약 최소, 최대값을 직접 지정하여 그 범위 안에서 난수를 발생시키려면 아래와 같이 공식을 이용하면 됩니다. 주로 게임에서 최소, 최대 데미지 사이의 데미지를 발생시킨다면 아래와 같이 사용하시면 됩니다.

 

rand() % (max - min + 1) + min

ex) 50 ~ 100 난수 발생 = rand() % (100 - 50 + 1) + 50

=> 마지막 50 더하기 전에 나온 결과는 0 ~ 50이고, 여기에 50을 더하면 50 ~ 100의 난수를 생성


 

🟦 난수 생성 범위 제한

rand() 함수로 생성할 수 있는 난수의 범위는 RAND_MAX, 즉 32,767까지 생성할 수 있습니다. 물론 rand() 함수를 사용하더라도 약간의 편법으로 확장은 할 수 있지만 품질이 좋지 않고 오류가 많아 추천하지 않는 방법입니다.

 

그래도 혹시 다른 곳에서 정보를 얻고 사용할 수 있기 때문에 사용을 방지하기 위해 일단 아래에 공식을 적어놓겠습니다. 이런 방식을 사용하기 보다는 아래에서 따로 설명하는 random 라이브러리를 사용하는 것이 난수 품질 및 보안, 균등한 난수 분포를 지원하므로 추천합니다.

 

(int)(((double)rand() / ((double)RAND_MAX + 1.0)) * 40000)

 

위와 같이 사용하면 double 실수형으로 rand() 함수로 생성된 난수를 RAND_MAX + 1의 값으로 나누어 정규화를 거치면 [0, 1), 즉 0부터 1미만의 값이 랜덤하게 생성됩니다. 이 값을 원하는 범위의 숫자를 곱하면 일단 RAND_MAX 값보다는 큰 수를 생성할 수는 있지만, 값이 커지면 커질수록 오류율이 커집니다.

 

(double)rand() / (double)RAND_MAX + 1.0에서 최대값으로 32,767 / 32,768 = 0.99996948··· 값이 나오므로, 이 값에 곱하면 소수점 이하의 값으로 인해 최대값의 오차가 발생합니다.

ex) 0.99996948 * 40,000 = 39,998.xxx

 

RAND_MAX이하의 값으로 난수를 발생하는 것은 위의 rand() 함수를 이용하는 것만으로도 충분합니다. 다만, 큰 값의 난수를 생성하려면 기존의 C스타일 방식으로는 한계가 있으므로 아래의 random 라이브러리를 사용하는 것을 추천합니다.


 

3. C++ random 라이브러리로 난수 생성

C++11 이후에는 더 나은 난수 생성기를 제공하는 random 헤더가 도입되어 품질이 우수하고 다양한 난수 분포를 지원합니다. 아래는 사용 코드 예시입니다.

 

cpp
닫기
#include <iostream>
#include <random>
int main() {
std::random_device rd; // 하드웨어 기반 랜덤 엔진 (seed 생성용)
std::mt19937 gen(rd()); // Mersenne Twister 엔진
std::uniform_int_distribution<> dis(1, 100); // 1~100 범위의 균등 분포
for (int i = 0; i < 10; ++i) {
std::cout << dis(gen) << std::endl; // 난수 출력
}
return 0;
}

 

mt19937 같은 엔진을 통해서 균일하면서도 예측 불가능한 난수를 생성합니다. 또한 uniform_int_distribution으로 균등 분포 방식 또는 normal_distribution 정규 분포 등 다양한 분포 방식을 제공합니다.


구독 및 좋아요는 컨텐츠를 생산하는데 많은 도움이 됩니다. 😊

감사합니다.

저작자표시 비영리 변경금지 (새창열림)
  1. 1. rand() 함수 : 난수 생성
  2. 2. rand() 사용법
  3. 🟦 최소, 최대 범위 지정해서 생성하기
  4. 🟦 난수 생성 범위 제한
  5. 3. C++ random 라이브러리로 난수 생성
'프로그래밍/C++' 카테고리의 다른 글
  • C++ cin input 입력 버퍼 초기화하는 방법. 잘못된 입력 초기화 및 개행 문자 초기화
  • [프로그래밍 이론] 아스키(ASCII) 코드란 무엇인가?
RightNowHJ
RightNowHJ
온갖 잡다한 IT 관련 지식 모아모아 공유하는 블로그 (옛 LeePorter 블로그 이전)
  • RightNowHJ
    잡식성 개발자의 블로그
    RightNowHJ
  • 전체
    오늘
    어제
    • 분류 전체보기 (67)
      • IT 활동 (44)
        • 티스토리 (16)
        • 소프트웨어 (13)
        • AI (15)
      • 프로그래밍 (12)
        • 언리얼엔진 (9)
        • C++ (3)
      • 일상생활 (11)
        • 이슈모아보기 (5)
        • 실생활지식 (5)
        • 재테크 (1)
  • 블로그 메뉴

    • 홈
    • 태그
    • 방명록
  • 링크

  • 공지사항

  • 인기 글

  • 태그

    Unreal Engine
    블로그
    유틸리티
    티스토리챌린지
    stable diffusion
    언리얼 엔진
    sd 1.5
    부담부 증여
    Utility
    WEBUI
    티스토리
    셀프 등기
    AI 이미지
    AdSense
    소프트웨어
    을사년
    UE5
    부동산
    플러그인
    hELLO 스킨
    웹 ui
    오블완
    언리얼5
    광고
    메타 퀘스트
    다크모드
    수동 광고
    Meta Quest
    스테이블 디퓨전
    구글 애드센스
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.0
RightNowHJ
C/C++ 랜덤 난수 rand() 사용법 및 다양한 구현 방식

개인정보

  • 티스토리 홈
  • 포럼
  • 로그인
상단으로

티스토리툴바

단축키

내 블로그

내 블로그 - 관리자 홈 전환
Q
Q
새 글 쓰기
W
W

블로그 게시글

글 수정 (권한 있는 경우)
E
E
댓글 영역으로 이동
C
C

모든 영역

이 페이지의 URL 복사
S
S
맨 위로 이동
T
T
티스토리 홈 이동
H
H
단축키 안내
Shift + /
⇧ + /

* 단축키는 한글/영문 대소문자로 이용 가능하며, 티스토리 기본 도메인에서만 동작합니다.