Ce face std::normal_distribution
Multe mărimi reale au distribuție normală: înălțimea oamenilor, erori de măsurare, notele la un examen mare. Valorile se adună în jurul mediei, iar cele foarte depărtate sunt rare: circa 68% se află la cel mult o abatere standard de medie și circa 95% la cel mult două.
Fără argumente, media este 0 și abaterea standard este 1. Valorile nu sunt limitate: poate apărea, rar, și un număr foarte depărtat de medie.
Parametri
| Parametru | Descriere |
|---|---|
medie |
Centrul distribuției. |
abatere_standard |
Cât de împrăștiate sunt valorile (mai mare decât 0). |
Ce returnează
La fiecare apel, un double.
Exemple
Exemplul 1: Înălțimi simulate
Media și proporția calculate din 10000 de valori sunt apropiate de cele teoretice (170 cm și aproximativ 68%). Generatorul std::mt19937 cu seed fix produce aceleași numere pe orice compilator, dar modul în care o distribuție le transformă nu este fixat de standard. Rezultatul de mai jos este cel dat de libc++ (Clang); cu GCC sau MSVC, același seed poate da alte valori.
#include <cmath>
#include <print>
#include <random>
int main() {
std::mt19937 gen(5);
std::normal_distribution<double> inaltime(170.0, 8.0);
const int n = 10000;
double suma = 0;
int aproape = 0;
for (int i = 0; i < n; ++i) {
double h = inaltime(gen);
suma += h;
if (std::abs(h - 170.0) <= 8.0) {
++aproape;
}
}
std::println("Media: {:.1f} cm", suma / n);
std::println("Între 162 și 178 cm: {:.0f}%", 100.0 * aproape / n);
}
Rezultat
Media: 170.1 cm
Între 162 și 178 cm: 68%
Exemplul 2: Histogramă text
Generatorul std::mt19937 cu seed fix produce aceleași numere pe orice compilator, dar modul în care o distribuție le transformă nu este fixat de standard. Rezultatul de mai jos este cel dat de libc++ (Clang); cu GCC sau MSVC, același seed poate da alte valori.
#include <cmath>
#include <map>
#include <print>
#include <random>
#include <string>
int main() {
std::mt19937 gen(42);
std::normal_distribution<double> nota(7.0, 1.5);
std::map<long, int> histograma;
for (int i = 0; i < 2000; ++i) {
long n = std::lround(nota(gen));
if (n >= 1 && n <= 10) {
++histograma[n];
}
}
for (auto [n, cate] : histograma) {
std::println("{:>2} {}", n, std::string(cate / 20, '#'));
}
}
Rezultat
2
3
4 ###
5 ###########
6 ####################
7 #########################
8 ####################
9 ###########
10 ####
Greșeli frecvente
- Dai abaterea standard negativă sau 0: comportament nedefinit.
- Folosești valorile ca note sau vârste fără să le limitezi: distribuția normală poate da și valori sub 1 sau peste 10. Aplică
std::clampsau respinge-le.
Comenzi înrudite
std::uniform_real_distribution: Produce numere cu virgulă aleatorii, distribuite uniform în intervalul [a, b).std::mt19937: Generatorul Mersenne Twister: numere pseudo-aleatorii rapide și de calitate, reproductibile cu un seed fix.std::lerp: Interpolare liniară: valoarea aflată la fracțiunea t pe drumul dintre a și b (a + t·(b − a)).