Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

Красавин Компютерныы практикум в среде МатЛаб 2015

.pdf
Скачиваний:
121
Добавлен:
12.11.2022
Размер:
9.22 Mб
Скачать

fgets считывает строку из файла, сохраняя символ конца строки, а fgetl считывает строку из файла, удаляя символ конца строки. Для применения всех вышеперечисленных функций чтения информации из файла требуется сначала открыть файл, а после считывания информации закрыть файл.

Как правило, функции fgetl и fgets используются внутри конструкций for или while. Функции fscanf и textscan могут считать всю информацию из файла в одну переменную. В плане принадлежности к уровню можно считать, что эти две функции занимают промежуточное место между функцией load и такими низкоуровневыми функциями, как fgetl. При работе с ними не требуется никаких конструкций типа for или while, файл будет автоматически полностью считан в одну переменную.

Функция fgetl предоставляет больше возможностей контролировать, каким образом будет считана информация из файла, по сравнению с другими функциями чтения. Функция fgetl считывает одну строку из файла в виде строковой переменной (string), затем с помощью функций работы со строками считанную информацию можно преобразовывать. Так как функция fgetl считывает одну строку, ее, как правило, помещают в циклическую конструкцию, которая считывает файл до конца. Функция feof возвращает логическую единицу, если достигнут конец файла, и логический нуль в ином случае. Таким образом, можно составить алгоритм считывания информации из файла:

делается попытка открыть файл; проверяется, был ли открыт файл успешно или нет;

если файл открыт успешно, то запускается цикл, работающий до тех пор, пока не будет достигнут конец файла;

для каждой строки из файла:

считывание в строковую переменную (string); преобразование считанной информации;

делается попытка закрыть файл; проверяется, был ли закрыт файл успешно или нет.

91

На языке MatLab приведенный алгоритм соответствует следующей конструкции:

fid = fopen('filename'); % если функция fopen

используется без дополнительных аргументов, то применяется аргумент 'r', установленный по умолчанию

if fid == -1

disp('Файл не удается открыть')

else

while feof(fid) == 0 % Считывание одной строки в строковую переменную

aline = fgetl(fid);

...

% Здесь следует использовать функции работы со строками, для того чтобы извлечь из строковой переменной aline числа, строки и т.д.

...

end

closeresult = fclose(fid); if closeresult == 0

disp('Файл успешно закрыт')

else

disp('Файл не удается закрыть')

end

end

Условие в цикле while можно интерпретировать как «делать цикл пока не достигнут конец файла». Это условие можно записать альтернативным способом:

while ~feof(fid)

Предположим, что имеется файл subjexp.dat, который содержит в каждой строке некоторое число, далее пробел и

92

некоторый символ. С помощью функции type можно отобразить информацию, содержащуюся в данном файле:

type subjexp.dat

5.3 a

2.2 b

3.3 a

4.4 a

1.1 b

Такой файл невозможно считать в матричную переменную с помощью функции load, так как он содержит одновременно и числа, и текст. Однако с помощью функции fgetl можно считать данный файл построчно в строковые переменные, и, используя функции работы со строками, отформатировать информацию.

Пример 8.1.

fid = fopen('subjexp.dat'); if fid == -1

disp('Файл не удается открыть')

else

while feof(fid) == 0 aline = fgetl(fid);

[num, charcode] = strtok(aline); %Разделение строки на число и символ

fprintf('%.2f %s\n', str2double(num), charcode)

end

closeresult = fclose(fid); if closeresult == 0

disp('Файл успешно закрыт')

else

end

В результате выполнения приведенных команд получим:

5.30

a

2.20

b

3.30

a

4.40

a

1.10

b

Файл успешно закрыт

93

В примере 8.1 на каждой итерации цикла функция fgetl считывает одну строку в строковую переменную aline. Функция strtok разделяет строку на две строки с именами num и charcode. Далее тип переменной num преобразуется в число с плавающей точкой с помощью функции str2double.

Часто для считывания информации из файла в матричную переменную используется функция fscanf:

mat = fscanf(fid, 'format', [dimensions])

Здесь функция fscanf считывает информацию из файла, имеющего идентификатор fid, в матричную переменную mat. Переменная format должна содержать специальные аргументы для преобразования типов. Размерность матричной переменной mat определяется переменной dimensions; если количество значений в файле не известно, то следует использовать значение inf. Пример 8.1 может быть переписан с использованием функции fscanf следующим образом:

fid = fopen('subjexp.dat');

mat = fscanf(fid,'%.2f %s',[2, inf])

mat =

5.30 a

2.20 b

3.30 a

4.40 a

1.10 b fclose(fid);

В примере 8.2 рассматривается применение функции fscanf для обработки сложно отформатированной информации.

Пример 8.2. Предположим, что имеется файл mymeas.dat, содержащий следующую информацию: в первой строке находится заголовок файла, который требуется проигнорировать; во второй строке указано количество блоков измерений; третья строка – пустая; затем следуют блоки измерений. Блоки измерений представляют собой также сложную конструкцию: каждый блок

94

состоит из трех частей, при этом первая часть содержит информацию о времени измерения, вторая – о дате, затем следуют четыре строки по четыре значения измерения в каждой:

Measurement Data

N=3

12:00:00 01-Jan-1977

4.216.55 6.78 6.55

9.150.35 7.57 NaN

7.928.49 7.43 7.06

9.59 9.33 3.92 0.31 09:10:02

23-Aug-1990

2.766.94 4.38 1.86

0.463.17 NaN 4.89

0.979.50 7.65 4.45

8.23 0.34 7.95 6.46 15:03:40

15-Apr-2003

7.096.55 9.59 7.51

7.54

1.62

3.40

2.55

NaN 1.19

5.85

5.05

6.794.98 2.23 6.99

Такой файл можно считать с помощью функции fscanf в структуру, используя нижеприведенный код:

filename = 'mymeas.dat'; % название файла measrows = 4; % количество строк meascols = 4; % количество столбцов

fid = fopen(filename); % открытие файла

finfo = dir(filename); % считывание информации о файле fsize = finfo.bytes; % определение размера файла

if fsize > 0 % если файл – не пустой, то

% считывание верхней части файла и запись значения переменной

N

N = fscanf(fid, '%*s %*s\nN=%d\n\n', 1);

% считывание файла по блокам block = 1;

while ~feof(fid) % пока не достигнут конец файла

95

%считывание и запись в структуру mystruct по ячейкам переменных mtime, mdate, means

%считывание mtime, в виде строковых данных, 1 строка mystruct(block).mtime = fscanf(fid, '%s', 1);

%считывание mdate, в виде строковых данных, 1 строка mystruct(block).mdate = fscanf(fid, '%s', 1);

%считывание meas, в виде переменных с плавающей точкой, 4 строки, по 4 значения в каждой

mystruct(block).meas = fscanf(fid, '%f', [measrows, meascols])'; % (двумерный массив)

block = block + 1; % итерация по блокам

end

end

fclose(fid); % закрытие файла

Функция dir предназначена для считывания информации о файле в структуру finfo, которая впоследствии используется для определения размера файла. Считывание файла в структуру mystruct производится блоками, количество которых определяется с помощью второй строки файла. Каждый блок структуры делится на три части, которые записываются в соответствующую ячейку структуры, mtime, mdate или meas с помощью функции fscanf.

Еще одной функцией низкоуровнего общения с файловой системой является textscan. Функция textscan считывает информацию из файла и сохраняет ее в виде массива ячеек (cell array). Пример использования функции textscan:

cellarray = textscan(fid, 'format');

Так же, как и при использовании функции fscanf, переменная format должна содержать специальные символы для преобразования типов, а переменная fid – идентификатор файла. Переменная format описывает тип столбцов в массиве ячеек cellarray. Например,

fid = fopen('subjexp.dat');

96

subjdata = textscan(fid,'%f %c'); fclose(fid)

Аргумент %f %c означает, что каждая строка файла содержит число с плавающей точкой и один символ через пробел. Функция textscan создает массив subjdata, состоящий из двух ячеек. Первая ячейка – это столбец, содержащий числа; вторая – столбец, содержащий символы:

subjdata subjdata =

[5x1 double] subjdata{1}

ans = 5.3000 2.2000 3.3000 4.4000 1.1000

subjdata{2} ans =

a b a a b

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

Функция fprintf обеспечивает построчную запись информации в файл:

fprintf(fid, 'format', variable);

97

Функция fprintf возвращает количество байтов, которые были записаны в файл. Запись происходит в файл с идентификатором fid. По умолчанию при отсутствии идентификатора файла функция fprintf выводит информацию на экран, так как экран является основным устройством вывода информации. Переменная format должна содержать специальные аргументы для преобразования типов. Переменная variable содержит информацию для записи. Пример использования fprintf:

fid = fopen('tryit.txt', 'w'); % аргумент 'w'

означает, что файл создается (или перезаписывается) для записи информации

for i = 1:3

fprintf(fid, 'Цикл %d\n', i);

end fclose(fid);

Для того чтобы проверить, что было записано в файл tryit.txt, считаем его построчно, применяя функцию fgetl:

fid = fopen('tryit.txt'); while ~feof(fid)

aline = fgetl(fid); disp(aline)

end

Цикл 1 Цикл 2 Цикл 3

fclose(fid);

Функцию fprintf можно применять и к матричным переменным:

mat = [20 14 19 12; 8 12 17 5]

mat =

98

20 14 19 12

8 12 17 5

fid = fopen('randmat.dat','w'); fprintf(fid,'%d %d\n’,mat); fclose(fid);

type randmat.dat

20 8

14 12

19 17

12 5

Для того чтобы корректно записать матричную переменную mat, в функции fprintf прописывается второй аргумент %d %d\n, который означает, что матрица, которую нужно записать, состоит из двух столбцов. Далее, поскольку mat является матричной переменной, для считывания информации из файла randmat.dat можно применить функцию load:

load randmat.dat >> randmat

randmat = 20 8 14 12 19 17 12 5

randmat' % с помощью транспонирования randmat можно восстанановить вид переменной mat

ans =

20 14 19 12

8 12 17 5

99

Функцию fprintf можно также использовать для добавления информации в файл. В данном случае файл должен быть открыт функцией fopen следующим образом:

fid = fopen('filename', 'a')

Второй аргумент в функции fopen означает, что файл открывается с целью добавления информации в файл.

8.4.Mat-Файлы

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

файлами расширений .dat, .txt и т.д., MatLab имеет функции для считывания и записи переменных в специальные файлы, которые имеют расширение .mat и называются mat-файлами. Данные файлы отличны от файлов с расширениями .dat, .txt и т.д.; кроме прочего они содержат названия переменных и их тип. Записываются mat-файлы в бинарном формате.

Переменные могут быть записаны, считаны и добавлены в matфайл:

save filename variablename

Здесь filename – имя файла (без расширения); variablename – сохраняемая переменная. С помощью функции save в mat-файл можно сохранять переменные любого типа, в том числе и матричные:

mymat = rand(3,5); save mat mymat who -file mat

Your variables are: mymat

100

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]