Организация данных в ЭВМ и основы программирования (1017140), страница 13
Текст из файла (страница 13)
Перед именем может ставиться так называемый путь к файлу – имя диска или имя текущего каталога и имена каталогов вышестоящих уровней.
Имя диска содержит одну из латинских букв, после которой ставится двоеточие. Имена А: и В: относятся к дисковым накопителям на гибких дисках, остальные – к жёстким дискам.
Если имя диска не указано, подразумевается устройство по умолчанию – то, которое было установлено в операционной системе перед началом работы программы.
За именем диска может указываться имя каталога, содержащего файл. Если имени каталога предшествует обратная косая черта ( \ ), то путь к файлу начинается из корнего каталога, если черты нет – из текущего каталога, установленного в системе по умолчанию. За именем каталога может следовать одно или несколько имён каталогов нижнего уровня. Каждому из них должна предшествовать обратная косая черта. Весь путь к файлу отделяется от имени файла обратной косой чертой. Максимальная длина имени вместе с указанием пути – 79 символов.
10.4. Описание файлового типа
Файловый тип или переменную файлового типа можно задать одним из трёх символов:
имя = file of тип;
имя = text;
имя = file;
Пример: Var finp: text;
Fout: file of string;
const name = ‘c:\dir\subdir\out.txt;
…………………………
Во время выполнения программы данные файла поступают в память компьютера и преобразуются в тот тип данных, который оъявлен в программе.
Общий вид описания файлового типа:
Type имя = File of тип;
Число компонентов в определении файлового типа в отличие от массива не фиксируется. Тип компонентов файла может быть любым, кроме файлового.
Пример:
Type Number = file of integer; {файл целых чисел}
Symb = file of ‘A’..’Z’; {файл прописных латинских букв}
Стандартный тип Text определяет тип–файл, содержащий символы, объединённые в строки. Следует иметь в виду, что тип Text в Турбо-Паскале не эквивалентен типу file of char.
В Турбо-Паскале можно использовать файл без типа, при определении которого не указывается тип компонент. В этом случае работа с файлом осуществляется на физическом уровне, в соответствии с внутренним форматом его данных. При этом реальные компоненты файла могут иметь и различные типы.
Пример: Type untyp = file;
Итак, в Паскале файловый тип описывается следующим образом:
type T = TValue;{ тип компоненты файла }
< имя файлового типа > = file of T;
Как обычно, файловый тип может быть введен в употребление в разделе типов, как было описано выше, либо непосредственно задан при описании переменных, например: var myfile: file of T;
Файлы, имена которых включаются в список заголовка программы, называются внешними файлами, они существуют вне программы. Если же имена файлов не внесены в список заголовка программы, то такие файлы существуют только во время выполнения программы и называются внутренними. Внутренние файлы носят в основном вспомогательный характер. Стандартный ввод осуществляется из файла input, а вывод в файл output.
10.5. Файловая переменная
Каждому файлу ставится в соответствие уникальная файловая переменная. Кроме того, обычными программными средствами нельзя создать программы, позволяющие взаимодействовать с устройствами ввода-вывода, кроме терминалов пользователя. Своеобразным «окном» между программами и внешними устройствами является файловая переменная. Поэтому в каждой программе, где предусматривается взаимодействие с устройствами ввода-вывода, организуется определённым образом логическая связь устройства ввода-вывода с файловой переменной.
Пример:
Type ZAP = Record
FIO: array [1..10] of char;
God: Integer
end; { of Record }
F = File of ZAP;
Тогда любая переменная типа F – это последовательный файл, состоящий из записей. Каждая запись имеет 2 поля: FIO (фамилия) и God (год рождения).
Переменные файлового типа, как и обычные переменные, описываются в разделе переменных: Var C: F;
С переменной С автоматически связана некоторая буферная переменная, относящаяся к типу компонентов файла и представляющая собой своеобразное «окно», через которое можно просматривать или записывать очередные компоненты. В любой момент доступен только один компонент файла – тот, что виден через буферную переменную.
С каждой файловой переменной связано понятие текущего указателя, это некоторая скрытая переменная, означающая (или указывающая) конкретный элемент файловой структуры. Все элементы файла считаются пронумерованными, начиная с нулевого.
Описание файла в разделе описания переменных:
Var Myfile: File of Integer;
Это означает, что в прграмме под файловым именем Myfile понимается неопределённое количество целых чисел, которые в виде физического файла могут располагаться на некотором внешнем уровне.
С каждым элементом последовательного файла тоже связано понятие текущего указателя. Поскольку все действия с данным файлом связаны с его элементами, необходимо знать, какой именно элемент файла подвергается обработке. Для этого используется текущий указатель.
Если программа взаимодействует с внешними файлами (хранимыми на диске), то файлы должны быть описаны в программе либо явно в разделе переменных Var, либо с использованием раздела типов Type.
Var имя файла: File of базовый тип
Пример: Var FT: File of char; (* файл символьных данных *)
Finp: File of real; (* файл действительных данных *)
М: File of integer; (* файл целых данных * )
Файлы символьных данных называются текстовыми файлами.
Определение данных с использованием раздела описания типов Type делает программу более универсальной и упрощает отладку программы.
Type имя типа = File of базовый тип;
Var имя переменной: имя типа;
Пример: Type T = File of Char;
Var FT: T;
Здесь Т – введённое нами имя типа.
Пример описания файловых типов и переменных:
Type SS = file of Char;
Person = record
name: string [20];
adress: string [25];
sex: ( man, woman );
day: 1..31;
month: 1..12;
year: 1900..2000
end;
Var F1, F2: SS;
Table: file of string [50];
Base: file of person;
Data: file of integer;
Файловые переменные имеют специфическое применение. Над ними нельзя выполнять никакие операции (присваивать значение, сравнивать и т.д.). Их можно использовать лишь для выполнения операций с файлами (чтения, записи, удаления файла и т.д.). Кроме того, через файловую переменную можно получить информацию о конкретном файле (тип, параметры, имя файла и т.д.).
10.6. Операции над файлами
Язык Паскаль не содержит встроенных операций по обработке файловых переменных. Это характерно для многих языков программирования высокого уровня. Поэтому для реализации операций над файловыми переменными базовое ядро Паскаля требует определённого интерфейса с физическим аппаратным сооружением. Этот интерфейс реализуется с помощью специальных процедур и функций.
Операции по установке связей между файловой переменной и внешним устройством или внешним файлом на магнитном носителе, т.е. операции по открытию файлов, а так же операции по «развязке» этих связей, т.е. закрытию файлов реализуются процедурами:
Assign Rewrite Close
Reset Append Flush
Связывание файловой переменной с именем файла осуществляется обращением к встроенной процедуре ASSIGN:
Assign ( файловая переменная, имя файла ).
Здесь имя файла – переменная или константа типа String. Имя должно быть написано в соответствии с правилами MS DOS, может включать путь и не должно превышать 79 символов. Если строка имени пустая, осуществляется связь со стандартным файлом ввода или вывода (как правило, консолью).
Файл становится доступен программе только после выполнения особой процедуры открытия файла. Эта процедура заключается в связывании ранее объявленной файловой переменной с именем существующего или вновь создаваемого файла, а также в указании направления обмена информации: чтение из файла или запись в него.
Примеры:
1) Установление связи с внешним файлом на магнитном носителе. В этом случае имя внешнего файла представляет собой спецификацию файла:
Assign (Namefaile,’C:\direct\tfile.dat’);
Assign (Kandy,’D:\direct\sadry\fio.dat’);
2) Установление связи программного файла с внешним устройством. Для ввода с клавиатуры, если далее следует операция считывания данных; либо вывода на экран дисплея, если далее следует операция записи данных:
Assign (inputfile,’CON’);
3) Для вывода данных на печатающее устройство (допускается подключение до трёх печатающих устройств): LPT1 (синоним PRN), LPT2 и LPT3.
Assign ( Outhut,’LPT1’ );
4) Для последующего обмена информацией по коммуникационным каналам. Смысл записи псевдофайлов COM1 (или синоним AUX) либо СОМ2 определяется конкретным внешним устройством. Например, это может быть «мышь» или графопостроитель (плотер), либо узел при сетевой связи компьютеров:
Assign ( interfile,’COM1’ );
5) Установление связи с фиктивным внешним устройством. Например, при отладке программы вывод информации блокируется, но конкретная работа программы при этом не нарушается:
Assign (myfile,’NUL’);
Реализация операций обмена данными
После установления связи необходима инициализация этой связи, т.е., как принято говорить, необходимо открытие файла. Иницировать файл – означает указать для этого файла направление передачи данных. В Паскале можно открыть файл для двух видов взаимодействия: чтения и записи.
Эта операция в общем случае выполняется следующими процедурами:
Reset (файловая переменная, размер записи);
Reset (файловая переменная);
Rewrite (файловая переменная);
Rewrite (файловая переменная, размер записи);
Append (файловая переменная);
Основные процедуры обработки файлов
Reset (F) – подготовка чтения файла F. При этом указатель позиции помещается в начало файла. Если файл не пустой, то переменной F присваивается значение его первого компонента, а функция eof (F) = false. Параметр «размер записи» указывается лишь в случае обработки нетипизированных файлов. В результате обработки процедуры Reset, если соответствующий файл обнаружен, текущий указатель устанавливается в начале файла, т.е. на нулевом элементе файла. Если же внешний файл не обнаружен, то вырабатывается условие ошибки. Оператор процедуры reset(f) переводит файл f в режим чтения и устанавливает окно на первую позицию файла. Оператор процедуры read(f,v) присваивает переменной v значение текущей компоненты из файла f и передвигает окно на следующую позицию. Процедура reset может применятся к одному и тому же файлу несколько раз и при этом содержимое его не изменяется.
Rewrite (F) – подготовка записи в файл. Текущее значение файловой переменной F становится равным emply (пустой). Функция eof (F) = true. Может записывать новый файл. Оператор процедуры rewrite(f) устанавливает файл в режим записи, если раньше в этот файл были записаны какие-то данные, то они теряются. Оператор процедуры write(f,x) записывает в файл f очередную компоненту x, после чего окно сдвигается на следующую позицию. Общий вид оператора подготовки запист:
Rewrite (файловая переменная, [имя файла]);
Если внешнее имя файла опущено при открытии файла для записи, то файловая переменная трактуется как временный файл, который по окончанию работы программы ликвидируется. Параметр. «размер записи» указывается лишь в случае нетипизированного файла. В результате обработки процедуры ReWrite, если соответствующий файл обнаружен, текущий указатель устанавливается в начале файла, на место нулевого элемента записывается «символ конца файла». Другими словами, процедура rewrite очищает содержимое файла, а текущий указатель устанавливается в позицию готовности записи нулевого элемента.
Непосредственные операции ввода–вывода выполняются процедурами read и write. Обращения к этим процедурам:
Read (файловая переменная, выражение);
Write (файловая переменная, выражение);
После открытия на запись файл считается пустым, а указатель устанавливается на начало; в этот файл затем можно последовательно заносить информацию из буферной переменой при помощи процедуры write:
write (файловая переменная);
Если файл с таким именем уже существует, то вся информация, хранившаяся ранее в этом файле, становится недоступной. Процедура Write записывает в файл очередной компонент и переставляет указатель на свободное место. Таким образом, число компонентов файла увеличивается на единицу.
В принципе все операции создания и чтения последовательного файла можно сформировать из приведённых простых процедур и стандартной функции eof. На практике же часто полезно совмещать перемещение по файлу с доступом к буферной переменной. Поэтому введём две новые процедуры Read и Write следующим образом:
Read (F,X), где Х – некоторая переменная.
Write (F,Y), где Y – некоторое выражение.
Read и Write – специальные процедуры, распространённые для работы с переменным числом параметров (Х1,Х2,…,ХN – переменные, а Y1,Y2,…,YN – выражения).