Рандомні числа
Доволі часто виникає потреба згенерувати рандомне число. Для прикладу, якщо ви пишете програму яка імітує випадання грального кубика. Або вам потрібні довільні числа щоб заповнити масив.
У мові програмування рандомні числа поділяють на два види:
Псевдорандомними називають ті числа які програма обирає самостійно але з кожним запуском вони повторюються.
Щоб згенерувати рандомне число (на початку воно буде псевдорандомним) варто скористатися функцією Вона генерує ціле додатне число.
Розглянемо наступну програму. В ній змінна два рази отримує довільне рандомне число. Для демонстрації, що ці числа є різними ми значення цієї змінної двічі виводимо.
#include <iostream>
int main()
{
int a;
a = rand();
std::cout << a << std::endl;
a = rand();
std::cout << a << std::endl;
return 0;
}
Але при кожному запуску програми ці числа будуть однаковими. Тому, їх називають псевдорандомними.
Цього буває достатньо щоб заповнити масив і перевірити працездатність програми але в реальності цього занадто мало.
Для того щоб мати можливість псевдорандомні числа можна використовувати функцію та вказувати в якості її аргумента довільне ціле додатне число. Цю функцію варто записувати лише один раз. Краще за все на початку програми або безпосередньо перед першим використанням
#include <iostream>
int main()
{
srand(1);
int a;
a = rand();
std::cout << a << std::endl;
a = rand();
std::cout << a << std::endl;
return 0;
}
Міняючи число в якості аргумента функції ви будете отримувати різні псевдорандомні числа. Але при запуску програми з одним і тим же числом ви знову ж таки будете мати однакові результати.
Для того щоб гарантовано отримувати кожного разу новий результат вам варто підключити бібліотеку або Також в якості аргументу функції варто вказати або
#include <iostream>
#include <ctime>
int main()
{
srand(time(0));
int a;
a = rand();
std::cout << a << std::endl;
a = rand();
std::cout << a << std::endl;
return 0;
}
Коли в якості аргумента ви ставите то на справді ви вказуєте кількість секунд, що пройшло від до моменту запуску програми. Тому, ви і отримаєте різні результати.
Як помітно, результати бувають доволі різними. Якщо потрібно обмежити діапазон чисел, то можна зробити так:
rand() % max;
Де «max» це число ДО якого ви можете отримати рандомне число. В такій ситуації ви будете мати діапазон чисел від «0» до «max - 1».
Звісно, щоб отримати включно з максимальним числом ви можете вказувати на одиницю більше число. Тобто, коли хочете отримати діапазон чисел то можна вказати: Або:
Отже, щоб отримати діапазон чисел ВКЛЮЧНО з максимальним потрібно до максимального числа додати При цьому, якщо ви хочете додавати її окремо, то цей запис має бути обов’язково у дужках.
#include <iostream>
#include <ctime>
int main()
{
srand(time(0));
int a;
//числа від «0» до «14» включно
a = rand() % 15;
std::cout << a << std::endl;
return 0;
}
Якщо ж ви хочете отримати числа від якогось конкретного найменшого (вказати самостійно мінімальне число), то вам варто використати метод:
rand() % (max – min) + min;
І відповідно, якщо ви хочете мати включно з максимальним числом, то у дужках ще потрібно додати (або максимальне число враховувати разом з цією одиницею):
rand() % (max – min + 1) + min;
Наприклад:
#include <iostream>
#include <ctime>
int main()
{
srand(time(0));
int a;
//числа від «15» до «25» включно
a = rand() % (25 – 15 + 1) + 15;
std::cout << a << std::endl;
int max = 60, min = 50;
//числа від «50» до «60» включно
a = rand() % (max – min + 1) + min;
std::cout << a << std::endl;
return 0;
}
Давайте розберемося як це працює. Припустимо, ми хочемо отримати діапазон чисел Тоді, наший запис буде таким: Якщо ж до цього запису ми допишемо (тобто, отримаємо то і діапазон чисел збільшиться. Будемо мати і Тобто, максимальним числом вже буде Це ж в свою чергу буде дуже сильно збивати з пантелику, адже в якості максимального числа ми очікували
Відповідно, щоб уникнути подібних ситуацій ми зменшуємо максимальне числа, а потім повертаємо його до попереднього значення.
Дуже часто отримання рандомних чисел виносять в окрему функцію:
#include <iostream>
#include <ctime>
//оскільки часто в якості мінімально числа
//беруть "0", то ми можемо взяти його
//зі значенням за замовчуванням.
//якщо вам не лінь кожного разу
//передавати два аргументи функції,
//то можете скористатися таким записом:
//int randI(int min, int max)
int randI(int max, int min = 0)
{
return rand() % (max - min + 1) + min;
}
int main()
{
//зверніть увагу. Функцію "srand"
//ми вказуємо в головній програмі
srand(time(0));
int a;
//діапазон від 0 до 10
a = randI(10);
std::cout << a << std::endl;
//діапазон від 20 до 30
a = randI(30, 20);
std::cout << a << std::endl;
return 0;
}
Якщо ви хочете отримати дробові рандомні числа, то вам доведеться написати власну функцію. Відразу зауважимо, що таким числам варто вказувати кількість цифр після крапки (вказувати їх точність).
#include <iostream>
#include <cmath> //для використання функції pow
#include <ctime>
//створюємо функцію яка повертає
//рандомне дробове число
//із заданою кількістю цифр після крапки
//(із заданою точністю)
//функція отримує 3 аргументи:
//min - найменше число
//max - найбільше число
//precision - точність, кількість знаків після коми.
double randF(double min, double max, int precision)
{
double value;
//отримуємо довільне ціле число з точністю precision
value = rand() % (int)pow(10, precision);
//отримуємо число з крапкою
value = (value / pow(10, precision)) * (max - min) + min;
return value;
}
int main()
{
double number;
srand(time(0));
//Отримуємо число в межах від "0"
//до "2" з точністю "3" знаки після коми
number = randF(0, 2, 3);
std::cout << "number = " << number << std::endl;
return 0;
}
Як вже було сказано раніше рандомні числа дуже зручно використовувати для заповнення масивів. Наприклад:
#include <iostream>
#include <ctime>
int main()
{
srand(time(0));
int mas[2][3];
for(int i = 0; i < 2; i++)
{
for(int j = 0; j < 3; j++)
{
//діапазон чисел буде від "1" до "20" включно
mas[i][j] = rand() % 20 + 1;
}
}
for(int i = 0; i < 2; i++)
{
for(int j = 0; j < 3; j++)
{
std::cout << mas[i][j] << " ";
}
std::cout << std::endl;
}
return 0;
}