Генерация псевдослучайных чисел.

В языке Си есть возможность генерации т.н. псевдослучайных чисел, т.е. чисел, выглядящих для человека как случайные, хотя в действительности вычисляемых по некоторому алгоритму.

К числу функций, обеспечивающих генерацию псевдослучайных чисел, относятся random() и randomize(). Для их работы необходимо подключить заголовочный файл stdlib.h (годятся также и некоторые другие).

Собственно генерацию выполняет функция random. При обращении к ней в скобках надо указать число, задающее диапазон генерируемых чисел (обозначим его N). Результат функции - "случайное" целое число, равновероятно выбранное в диапазоне от 0 до N-1 (таким образом, получается N различных вариантов этого числа).

Если нам нужно случайное целое число в другом диапазоне, то достаточно прибавить к значению random() начало требуемого диапазона, "сдвинув" тем самым результат:

 

int a,b,x;

...

x=random(b-a+1)+a; // x - случайное число в диапазоне [a..b]

 

Аналогично можно получать и дробные числа.

Работа функции random() основана на использовании специальной статической ячейки памяти. При запуске программы эта ячейка получат некоторое значение (обычно 0), а затем при каждом обращении к функции random() новое очередное значение в этой ячейке вычисляется из предыдущего по достаточно сложному алгоритму. Исходя из текущего значения этой ячейки, вычисляется сам результат функции random(). Поэтому он не имеет никакой видимой связи с предыдущим ее результатом, что и создает "псевдослучайность" полученных чисел. Однако, при повторном запуске программы начальное значение этой ячейки вновь будет восстановлено, поэтому вся последовательность полученных псевдослучайных чисел повторится.

Если же мы хотим, чтобы последовательность генерируемых чисел различалась при каждом запуске программы, можно воспользоваться функцией randomize(). Она записывает в упомянутую ячейку значение текущего системного времени (с учетом сотых долей секунд, а также даты). Поскольку дата и время запуска программы не могут повториться (тем более - с точностью до сотых долей секунды), после вызова randomize() функция random() будет выдавать уже совершенно новую, практически непредсказуемую последовательность.

Поэтому обращение к randomize() достаточно сделать один раз в начале программы. Не стоит делать это в цикле, т.к. значение системного времени обновляется не более 100 раз в секунду, а цикл может выполниться быстрее, и тогда каждый вызов randomize() запишет в ячейку одно и то же значение, а следующие за ними вызовы random() дадут одинаковые результаты.

Пример программы, заполняющей массив случайными числами от 1 до 100:

 

int a[40], n, i;

...

randomize();

for (i=0; i<n; i++)

a[i]=random(100)+1;

 


16. Файлы в языке С

 

Файл – это набор данных, размещенный на внешнем носителе и рассматриваемый в процессе обработки и пересылки как единое целое. В файлах размещаются данные, предназначенные для длительного хранения.

В языке Си имеется большой набор функций для работы с файлами, большинство которых находятся в библиотеках stdio.h и io.h. Все они рассматривают файл как последовательность байт, из которой можно читать или в которую можно записывать данные различными способами. При работе с файлом (при открытии файла) создается указатель позиции в файле (аналогичный по назначению курсору на экране) - он указывает, в каком месте файла будет производиться чтение/запись. По мере выполнения операций чтения/записи этот указатель автоматически продвигается вперед, так что каждая последующая операция чтения/записи будет читать/записывать уже следующую информацию. Указатель можно также непосредственно устанавливать в нужную позицию.