КАТЕГОРИИ: Архитектура-(3434)Астрономия-(809)Биология-(7483)Биотехнологии-(1457)Военное дело-(14632)Высокие технологии-(1363)География-(913)Геология-(1438)Государство-(451)Демография-(1065)Дом-(47672)Журналистика и СМИ-(912)Изобретательство-(14524)Иностранные языки-(4268)Информатика-(17799)Искусство-(1338)История-(13644)Компьютеры-(11121)Косметика-(55)Кулинария-(373)Культура-(8427)Лингвистика-(374)Литература-(1642)Маркетинг-(23702)Математика-(16968)Машиностроение-(1700)Медицина-(12668)Менеджмент-(24684)Механика-(15423)Науковедение-(506)Образование-(11852)Охрана труда-(3308)Педагогика-(5571)Полиграфия-(1312)Политика-(7869)Право-(5454)Приборостроение-(1369)Программирование-(2801)Производство-(97182)Промышленность-(8706)Психология-(18388)Религия-(3217)Связь-(10668)Сельское хозяйство-(299)Социология-(6455)Спорт-(42831)Строительство-(4793)Торговля-(5050)Транспорт-(2929)Туризм-(1568)Физика-(3942)Философия-(17015)Финансы-(26596)Химия-(22929)Экология-(12095)Экономика-(9961)Электроника-(8441)Электротехника-(4623)Энергетика-(12629)Юриспруденция-(1492)Ядерная техника-(1748) |
Установка произвольной позиции в файле
Следующей по значимости для работы с файлами после уже рассмотренных системных функций является функция позиционирования в файле. Эта функция обозначается в MS Windows именем SetFilePointer и именем lseek в операционной системе Unix. Функция позиционирования позволяет организовать прямой доступ к данным в файле путем указания места в файле, с которого будет выполняться следующее чтение или запись. Функция позиционирования SetFilePointer для MS Windows на языке Си имеет прототип DWORD WINAPI SetFilePointer(HANDLE hFile, LONG ib, LONG* pDistanceToMoveHigh, DWORD metod), где hFile – хэндл позиционируемого файла, ib – число байтов, на которое будет перемещена текущая позиция в файле относительно точки отсчета (младшие 32 бита), metod – метод отсчета смещения в файле, pDistanceToMoveHigh – адрес старшего слова размещения количества байт, на которые требуется переместить текущую позицию в файле (при использовании файлов меньше 4 Гбайт этот параметр не используется – задается как NULL). Результирующая позиция после перемещения выдается функцией в качестве значения типа DWORD. При ошибке функция возвращает значение -1. Метод отсчета задается символическими константами FILE_BEGIN, FILE_CURRENT, FILE_END, которые определены в заголовочном файле. Следующий пример, представленный листингом 2.5.1, демонстрирует использование позиционирования файла в MS Windows.
#include <windows.h> #include <stdio.h> void main() {char buffer[100]="It was readed "; int len; DWORD cb, cbw1; HANDLE hstdout, fhandle; char fname[ ]="myresult.txt"; BOOL rc; len = strlen(buffer); hstdout = GetStdHandle(STD_OUTPUT_HANDLE); if (hstdout = = INVALID_HANDLE_VALUE) return; fhandle=CreateFile(fname, GENERIC_READ, FILE_SHARE_READ, 0, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0); if (fhandle= = INVALID_HANDLE_VALUE) return; rc=SetFilePointer(fhandle, 10, 0, FILE_BEGIN); if (rc= =NULL) return; rc=ReadFile(fhandle, buffer+len, 80, &cb, NULL); if (!rc) return; cb += len; WriteFile(hstdout, buffer, cb, &cbw1, NULL); CloseHandle(fhandle); getchar(); return; } Листинг 2.5.1. Программа для Windows
В начале программа получает от ОС хэндл стандартного вывода вызовом функции GetStdHandle. Затем выполняется открытие файла с доступом по чтению и нормальными атрибутами, причем в режиме доступности по чтению другим процессам. Действия по открытию задаются флагом OPEN_EXISTING, т.е. файл, указанный именем myresult.txt, должен уже существовать, иначе возникает ошибка, обнаруживаемая следующими командами. Предполагается использовать эту программу после выполнения программы, описанной листингом 2.3.1, которая и должна была создать файл с именем myresult.txt. Затем указатель текущей записи в файле устанавливается на 10 байт от начала файла, что выполняется вызовом функции SetFilePointer. Далее выполняется чтение из этого файла – с той позиции, которая была только что установлена, и прочитанный текст выводится на стандартный вывод функцией WriteFile. Файл закрывается, а программа завершается. В операционной системе Unix для установки текущей позиции в файле служит функция с прототипом off_t lseek (int handle, off_t pos, int whence), где тип данных off_t совпадает в простейшем применении Unix с типом int (в общем случае тип данных off_t определяется в заголовочном файле sys/types.h). В качестве значения параметра whence следует использовать символические константы SEEK_CUR, SEEK_SET, SEEK_END, определяющие соответственно отсчет изменения позиции от текущего положения, от начала файла и от его конца. Второй параметр – pos определяет относительное смещение позиции в файле от указанной параметром whence точки отсчета. Результирующая позиция файла выдается как значение функции lseek. В случае неудачи функция возвращает значение -1. Для использования больших файлов в современных версиях операционных разновидностей Unix предназначена модификация базовой функции позиционирования, имеющая прототип __off64_t lseek64 (int handle, __off64_t pos, int whence). Она отличается от своей предшественницы только применением 64-битных значений в качестве смещения в файле, задаваемого вторым аргументом и возвращаемым значением с употреблением соответствующих типов данных для таких значений. Можно и неявно использовать 64-битные смещения в обычных функциях позиционирования lseek (с описываемым обобщенным типом данных off_t), если перед заголовочными файлами программы определить символическую константу __USELARGEFILE64 (которая имеет два символа подчеркивания в начале имени), задав такое определение в виде #define __USELARGEFILE64 Следующий пример, представленный листингом 2.5.2, демонстрирует использование позиционирования файла в Unix и по своим действиям аналогичен программе из листинга 2.5.1.
#include <stdio.h> #include <string.h> #include <fcntl.h> int main() {char buffer[100]="Было прочитано "; int len, cb, cbw1; int hstdin=0, hstdout=1, fhandle; char fname[ ]="myresult.txt"; struct flock lock={F_RDLCK, SEEK_SET, 0, 0}; len = strlen(buffer); fhandle=open(fname, O_RDONLY); if (fhandle = = -1) exit(1); lseek(fhandle, 10, SEEK_SET); fcntl(fhandle, F_SETLKW, &lock); cb=read(fhandle, buffer+len, 80); cb += len; cbw1=write(hstdout, buffer, cb); lock.l_type=F_UNLCK; fcntl(fhandle, F_SETLK, &lock); close(fhandle); } Листинг 2.5.2. Программа для Unix
В этой программе сначала открывается файл с именем myresult.txt, причем только для чтения (флаг открытия O_RDONLY), затем позиционируется функцией lseek относительно начала (параметр SEEK_SET) на десятый байт. Потом устанавливается блокировка по чтению от данного процесса на весь файл, из файла читаются данные, которые приписываются к тексту в массиве buffer. Полученный текст выводится функцией write в стандартный файл вывода, снимается блокировка с файла, он далее закрывается, и программа завершается.
Дата добавления: 2014-01-05; Просмотров: 708; Нарушение авторских прав?; Мы поможем в написании вашей работы! Нам важно ваше мнение! Был ли полезен опубликованный материал? Да | Нет |