![]() Главная страница Случайная страница КАТЕГОРИИ: АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатикаИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханикаОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторикаСоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансыХимияЧерчениеЭкологияЭкономикаЭлектроника |
Потоки данных и декораторы потоков
Представим наиболее часто используемые классы для работы с потоками в виде следующих категорий. 1. Абстрактный класс System.IO.Stream. Это базовый класс для других классов, представляющих потоки. 2. Классы для работы с потоками, связанными с хранилищами. FileStream – класс для работы с файлами, как с потоками (пространство имён System.IO). MemoryStream – класс для представления потока в памяти (пространство имён System.IO). NetworkStream – работа с сокетами, как с потоками (пространство имён System.Net.Sockets). PipeStream – абстрактный класс из пространства имён System.IO.Pipes, базовый для классов-потоков, которые позволяют передавать данные между процессами операционной системы. 3. Декораторы потоков. DeflateStream и GZipStream – классы для потоков со сжатием данных (пространство имён System.IO.Compression). CryptoStream – поток зашифрованных данных (пространство имён System.Security.Cryptography). BufferedStream – поток с поддержкой буферизации данных (пространство имён System.IO). 4. Адаптеры потоков. BinaryReader и BinaryWriter – классы для ввода и вывода примитивных типов в двоичном формате. StreamReader и StreamWriter – классы для ввода и вывода информации в строковом представлении. XmlReader и XmlWriter – абстрактные классы для ввода/вывода XML. Элементы абстрактного класса Stream сведены в табл. 13. Таблица 13 Элементы абстрактного класса Stream
Класс Stream вводит поддержку асинхронного ввода/вывода. Для этого служат методы BeginRead() и BeginWrite(). Уведомление о завершении асинхронной операции возможно двумя способами: или при помощи делегата типа AsyncCallback, передаваемого как аргумент методов BeginRead() и BeginWrite(), или при помощи вызова методов EndRead() и EndWrite(), которые ожидают до окончания асинхронной операции. Статический метод Synchronized() возвращает оболочку для потока, которая обеспечивает безопасность при совместной работе нескольких потоков выполнения (threads). Использование методов и свойств класса Stream будет показано на примере работы с классом FileStream. Объект класса FileStream возвращается некоторыми методами классов FileInfo и File. Кроме этого, данный объект можно создать при помощи конструктора с параметрами, включающими имя файла и опции доступа к файлу. // создаём файл test.dat в текущем каталоге и записываем 100 байтов var fs = new FileStream(" test.dat", FileMode.OpenOrCreate); for (byte i = 0; i < 100; i++) { fs.WriteByte(i); }
// можно записать информацию из массива байтов // первый аргумент метода Write() – массив, второй – смещение // в массиве, третий – количество записываемых байтов byte[] info = {1, 2, 3, 4, 5, 6, 7, 8, 9}; fs.Write(info, 2, 4);
// возвращаемся на начало потока и читаем все байты fs.Position = 0; while (fs.Position < fs.Length) { Console.Write(fs.ReadByte()); }
// закрываем поток (и файл), освобождая ресурсы fs.Close(); Класс MemoryStream даёт возможность организовать поток в оперативной памяти. Свойство Capacity этого класса позволяет получить или установить количество байтов, выделенных под поток. Метод ToArray() записывает все содержимое потока в массив байтов. Метод WriteTo() переносит содержимое потока из памяти в другой поток, производный от класса Stream. Класс BufferedStream – это декоратор потока для повышения производительности путём буферизации данных. В примере кода BufferedStream работает с FileStream, предоставляя 20000 байтов буфера. То есть, второе физическое обращение к файлу произойдёт только при чтении 20001-го байта[13]. // записываем 100000 байтов в файл File.WriteAllBytes(" myFile.bin", new byte[100000]);
// читаем, используя буфер using (FileStream fs = File.OpenRead(" myFile.bin")) using (var bs = new BufferedStream(fs, 20000)) { bs.ReadByte(); Console.WriteLine(fs.Position); // 20000 } Классы DeflateStream и GZipStream являются декораторами потока, реализующими сжатие данных. Они различаются тем, что GZipStream записывает дополнительные данные о протоколе сжатия в начало и конец потока. В следующем примере сжимается и восстанавливается текстовый поток из 1000 слов. // формируем набор из 1000 слов var words = " The quick brown fox jumps over the lazy dog".Split(); var rnd = new Random(); var text = Enumerable.Repeat(0, 1000) .Select(i => words[rnd.Next(words.Length)]);
// using обеспечит корректное закрытие потоков using (Stream s = File.Create(" compressed.bin")) { using (var ds = new DeflateStream(s, CompressionMode.Compress)) { using (TextWriter w = new StreamWriter(ds)) { foreach (string word in text) { w.Write(word + " "); } } } }
using (Stream s = File.OpenRead(" compressed.bin")) { using (var ds = new DeflateStream(s, CompressionMode.Decompress)) { using (TextReader r = new StreamReader(ds)) { Console.Write(r.ReadToEnd()); } } }
|