Студопедия.Орг Главная | Случайная страница | Контакты | Мы поможем в написании вашей работы!  
 

Функция-элемент seekg



Прототип для перегруженной функции-компонента seekg:

istream& seekg(long pos);

istream& seekg(long offset, seek_dir dir);

Параметр pos в первой версии определяет абсолютное положение байта в потоке. Во второй версии параметр offset определяет относительное смещение, в зависимости от аргумента dir. Аргументы для последнего параметра:

ios::beg С начала файла

ios::cur С текущей позиции файла

ios::end С конца файла

Пример

const BLOCK SIZE = 80

char buff[BLOCK_SIZE] = "Hello World!";

f.open("CALC.DAT", ios::in | ios::out | ios::binary);

f.seekg(3 * BLOCK_SIZE); // продвинутся к блоку 4

f.read((const unsigned char*)buff, BLOCK_SIZE);

cout < buff < endl;

fclose ();

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

Рассмотрим пример файлового ввода/вывода прямого доступа. В листинге 10.3 приведен исходный код программы VIRTUAL.CPP и реализует виртуальный массив. Программа выполняет следующие задачи:

- Использует внутренний список имен для создания объекта виртуального массива.

- Отображает элементы неупорядоченного объекта виртуального массива.

- Сортирует элементы объекта виртуального массива.

- Отображает элементы сортированного объекта виртуального массива.

-

Листинг 10.3. Исходный код прогшраммы VIRTUAL.CPP

// C++ демонстрация файлового ввода/вывода прямого доступа

Программа листинга 10.3 объявляет класс VmArray. Этот класс моделирует динамический базирующийся на диске массив, который сохраняет все его элементы в двоичном файле прямого доступа. Заметьте, что в этом классе объявлен экземпляр класса fstream и что не существует указателя на динамический массив. Класс объявляет конструктор, деструктор и ряд функций-компонентов.

Конструктор класса имеет два параметра: Size и filename. Параметр Size задает размер виртуального массива. Параметр filename именует двоичный файл, который сохраняет элементы экземпляров класса. Конструктор открывает поток f, используя потоковую функцию open и передавая ей в качестве аргументов filename и выражение для режима работы с файлом ios::in | ios::out | ios::binary.

Это выражение указывает, что поток открывается для двоичного ввода/вывода (то есть режима прямого доступа). Если конструктор успешно открывает файловый поток, он заполняет файл пустыми строками. Деструктор класса выполняет простую задачу закрытия файлового потока f.

Функции setElem и getElem поддерживают прямой доступ к элементам массива. Эти функции используют потоковую функцию seekg, чтобы устанавливать указатель потока на соответствующий элемент массива. Затем функция setElem вызывает потоковую функцию write для сохранения элемента массива (передаваемый параметром str). Напротив, функция getElem называет потоковую функцию read, чтобы получить элемент массива (возвращаемый через аргумент str). Обе функции возвращают результат типа bad, который указывает на успешность операции ввода/вывода.

Класс VmArray также объявляет функцию BubbleSort для сортировки элементов виртуального массива. Эта функция использует функции-элементы getElem и setElem для доступа и свопинга элементов массива. Затем, наконец, запускается последняя функция-элемент display для элементов виртуального массива, которая посылает их на экран. Функция main выполняет следующие

задачи:

- Объявляет экземпляр arr класса VmArray. (Этот экземпляр сохраняет 10 строк в двоичном файле ARR.DAT)

- Присваивает случайное значение элементам экземпляра аот, используя цикл for (строки 97 и 98).

- Отображает несортированные элементы экземпляра arr, вызывая функцию-элемент display.

- Сортирует массив, вызывая функцию BubbleSort.

- Отображает сортированные элементы экземпляра arr.

Заключение

Сегодняшний урок представил краткое введение в библиотеку ввода/вывода C++ и вынес на обсуждение следующие вопросы:

- Общие функции ввода/вывода, включая open, close, good, fail и оператор!.

- Функция open открывает файловый поток ввода/вывода и поддерживает попеременный и множественный режимы ввода/вывода. Функция close закрывает файловый поток. Функции good и fail индицируют успешную или ошибочную, соответственно, потоковую операцию ввода/вывода.

- C++ позволяет выполнять последовательный потоковый ввод/вывод для текста с использованием операций < и >, так же как и при помощи потоковой функции getline. Операция < позволяет записать символы и строки (а также и другие предопределенные типы данных). Операция > применяется для

- получения символов. Функция getline позволяет вашему приложению считывать строки с клавиатуры или из текстового файла.

- Последовательный потоковый ввод/вывод двоичных данных использует потоковые функции write или read для записи или считывания данных из переменных любого типа.

- Потоковый ввод/вывод прямого доступа для двоичных данных использует функцию seekg в объединении с функциями read и write. Функция seekg позволяет вам передвигать потоковый указатель либо в абсолютное, либо в относительное положение в потоке.

Вопросы и ответы

Как можно эмулировать прямой доступ к строкам в текстовом файле?

Сначала считывайте строки из файла как текст, получайте длину строк (плюс два символа для конца каждой строки) и сохраняйте накапливаемую длину в специальном массиве. (Назовите его, например, lineIndex) Этот массив сохраняет позицию байта, где начинается каждая строка. Последний элемент массива будет содержать размер файла. Для доступа к строке номер i, используйте функцию seek или seekg, чтобы найти смещение для lineIndex[i]. Размер строки номер i равен lineIndex[i+1] - lineIndex[i+1].

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

Вам необходимо использовать потоковую функцию gcount() для получения ряда байт фактически читаемых в последнем неформатированном потоковом вводе. Вот функция copyStream:

void copyStream(fstreamit fin, fstreamil fout,

unsigned char* buffer, int buffSize)

{

int n;

while (fin. read (buffer, buffaize))

{

n = fin.gcount();

fout.write (buffer, n);

}

}





Дата публикования: 2014-11-28; Прочитано: 1850 | Нарушение авторского права страницы | Мы поможем в написании вашей работы!



studopedia.org - Студопедия.Орг - 2014-2024 год. Студопедия не является автором материалов, которые размещены. Но предоставляет возможность бесплатного использования (0.007 с)...