Введение
В этом лабораторном практикуме мы изучим, как приблизить значение π с помощью метода Монте-Карло на языке программирования C. Мы начнём с генерации случайных точек внутри единичного квадрата, затем подсчитаем количество точек, попадающих внутрь четверти окружности, чтобы вычислить приближение π. Наконец, мы выведем вычисленное приближение.
Лабораторная работа охватывает ключевые этапы метода Монте-Карло для оценки π, включая генерацию случайных точек, подсчёт точек внутри четверти окружности и использование отношения точек внутри к общему числу точек для вычисления приближения. Этот практикум демонстрирует практическое применение концепций исчисления и аналитической геометрии на языке программирования C.
Генерация случайных точек в единичном квадрате
В этом шаге мы научимся генерировать случайные точки внутри единичного квадрата с помощью языка программирования C, что является важной частью метода Монте-Карло для приближения значения π.
Сначала создадим новый файл C в каталоге ~/project для реализации генерации случайных точек:
cd ~/project
nano random_points.c
Теперь напишем код для генерации случайных точек:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define NUM_POINTS 10000
int main() {
// Инициализируем генератор случайных чисел
srand(time(NULL));
// Генерируем случайные точки в единичном квадрате
for (int i = 0; i < NUM_POINTS; i++) {
double x = (double)rand() / RAND_MAX;
double y = (double)rand() / RAND_MAX;
printf("Точка %d: (%.4f, %.4f)\n", i + 1, x, y);
}
return 0;
}
Рассмотрим код подробнее:
srand(time(NULL))инициализирует генератор случайных чисел текущим временем(double)rand() / RAND_MAXгенерирует случайное число в диапазоне от 0 до 1- Мы генерируем 10 000 случайных точек в единичном квадрате (0,0) до (1,1)
Компилируем и запускаем программу:
gcc random_points.c -o random_points
./random_points
Пример вывода:
Точка 1: (0.7234, 0.5678)
Точка 2: (0.2345, 0.9876)
...
Точка 10000: (0.1122, 0.3344)
Подсчёт точек внутри четверти окружности и приближение π
В этом шаге мы изменим предыдущую программу, чтобы подсчитать количество точек, попадающих внутрь четверти окружности, и использовать эту информацию для приближения значения π.
Обновим файл random_points.c:
cd ~/project
nano random_points.c
Замените предыдущий код следующим:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <math.h>
#define NUM_POINTS 100000
int main() {
// Инициализируем генератор случайных чисел
srand(time(NULL));
int points_inside_circle = 0;
// Генерируем случайные точки и подсчитываем точки внутри четверти окружности
for (int i = 0; i < NUM_POINTS; i++) {
double x = (double)rand() / RAND_MAX;
double y = (double)rand() / RAND_MAX;
// Проверяем, находится ли точка внутри четверти окружности
if (x*x + y*y <= 1.0) {
points_inside_circle++;
}
}
// Приближение π
double pi_approximation = 4.0 * points_inside_circle / NUM_POINTS;
printf("Общее количество точек: %d\n", NUM_POINTS);
printf("Точек внутри четверти окружности: %d\n", points_inside_circle);
printf("Приближение π: %.6f\n", pi_approximation);
printf("Точное значение π: %.6f\n", M_PI);
printf("Разница: %.6f\n", fabs(pi_approximation - M_PI));
return 0;
}
Компилируем программу с использованием математической библиотеки:
gcc random_points.c -o random_points -lm
./random_points
Пример вывода:
Общее количество точек: 100000
Точек внутри четверти окружности: 78540
Приближение π: 3.141600
Точное значение π: 3.141593
Разница: 0.000007
Рассмотрим ключевые изменения:
- Увеличено количество точек для повышения точности
- Добавлена логика подсчёта точек внутри четверти окружности
- Используется формула: π ≈ 4 * (количество точек внутри окружности) / (общее количество точек)
- Включено сравнение с точным значением π
Вывод приближения
На этом заключительном шаге мы улучшим нашу программу приближения π, создав функцию для вывода результатов и улучшив форматирование вывода.
Изменим файл random_points.c:
cd ~/project
nano random_points.c
Обновим код с новой функцией вывода и улучшенным выводом:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <math.h>
#define NUM_POINTS 1000000
// Функция для вывода результатов приближения
void print_pi_approximation(int total_points, int points_inside_circle) {
double pi_approximation = 4.0 * points_inside_circle / total_points;
printf("Результаты приближения π\n");
printf("=====================\n");
printf("Сгенерировано точек: %d\n", total_points);
printf("Точек внутри четверти окружности: %d\n", points_inside_circle);
printf("Приближённое значение π: %.8f\n", pi_approximation);
printf("Точное значение π: %.8f\n", M_PI);
printf("Абсолютная разница: %.8f\n", fabs(pi_approximation - M_PI));
printf("Точность приближения: %.4f%%\n",
(1 - fabs(pi_approximation - M_PI) / M_PI) * 100);
}
int main() {
// Инициализируем генератор случайных чисел
srand(time(NULL));
int points_inside_circle = 0;
// Генерируем случайные точки и подсчитываем точки внутри четверти окружности
for (int i = 0; i < NUM_POINTS; i++) {
double x = (double)rand() / RAND_MAX;
double y = (double)rand() / RAND_MAX;
// Проверяем, находится ли точка внутри четверти окружности
if (x*x + y*y <= 1.0) {
points_inside_circle++;
}
}
// Выводим результаты приближения
print_pi_approximation(NUM_POINTS, points_inside_circle);
return 0;
}
Компилируем и запускаем программу:
gcc random_points.c -o random_points -lm
./random_points
Пример вывода:
Результаты приближения π
=====================
Сгенерировано точек: 1000000
Точек внутри четверти окружности: 785398
Приближённое значение π: 3.14159200
Точное значение π: 3.14159265
Абсолютная разница: 0.00000065
Точность приближения: 99.9998%
Ключевые улучшения:
- Создана отдельная функция
print_pi_approximation() - Увеличено количество точек до 1 000 000 для большей точности
- Добавлено более подробное форматирование вывода
- Включён процент точности приближения
Резюме
В этом лабораторном практикуме мы изучили, как генерировать случайные точки внутри единичного квадрата с помощью языка программирования C, что является ключевым элементом метода Монте-Карло для приближённого вычисления значения π. Мы инициализировали генератор случайных чисел текущим временем и сгенерировали 10 000 случайных точек в единичном квадрате (0,0) до (1,1) с помощью функции rand().
Затем мы модифицировали программу, чтобы подсчитывать точки внутри четверти окружности и использовать эту информацию для приближения значения π. Мы сгенерировали 100 000 случайных точек и проверили, какие из них попали внутрь четверти окружности. Вычислив отношение точек внутри окружности к общему количеству точек, мы смогли оценить значение π.



