Encoding
.
Теперь проверим, как считываются файлы. Процесс чтения осложняется тем, что мы не знаем, пока не прочитаем файл, сколько строк он будет содержать (другими словами, сколько последовательностей (char)13 - (char)10
находится в файле). Решим эту проблему, считывая сначала файл в экземпляр класса StringCollection
, который находится в пространстве имен System.Collections.Specialized
. Этот класс создан для хранения множества строк, которые могут динамически увеличиваться. Он реализует два интересующих нас метода: Add()
, добавляющий строку в коллекцию, и CopyTo()
, который копирует коллекцию строк в обычный массив (экземпляр System.Array
). Каждый элемент объекта StringCollection
будет содержать одну строку файла.
Метод DisplayFile()
вызывает другой метод ReadFileIntoStringCollection()
, который реально считывает файл. После этого мы знаем, сколько имеется строк, поэтому можно скопировать StringCollection
в обычный массив фиксированного размера и передать этот массив в текстовое поле. Так как при создании копии копируются только ссылки на строки, а не сами строки, процесс будет достаточно эффективным:
void DisplayFile() {
StringCollection LinesCollection = ReadFileIntoStringCollection();
string [] LinesArray = new string[LinesCollection.Count];
LinesCollection.CopyTo(LinesArray, 0);
this.textBoxContents.Lines = LinesArray;
}
Второй параметр StringCollection.CopyTo()
указывает индекс в массиве назначения, где мы хотим начать размещение коллекции.
Теперь рассмотрим метод ReadFileIntoStringCollection()
. Мы используем StreamReader
для считывания каждой строки. Основной трудностью является необходимость подсчитывать считанные символы, чтобы не превысить емкость текстового поля:
ArrayList ReadFileIntoStringCollection() {
const int MaxBytes = 65536;
StreamReader sr = new StreamReader(ChosenFile);
StringCollection Result = new StringCollection();
int nBytesRead = 0;
string NextLine;
while ((NextLine = sr.ReadLine()) != null) {
nBytesRead += NextLine.Length;
if (nBytesRead > MaxBytes) break;
Result.Add(NextLine);
}
sr.Close();
return Result;
}
Код завершен.
Если выполнить ReadWriteText
— считать файл CivNegotiations
и затем сохранить его, то файл будет иметь формат Unicode. Это невозможно для любого из обычных оконных приложений: Notepad, Wordpad и даже наш собственный пример ReadWriteText
будут по- прежнему считывать файл и выводить его правильно в Windows NT/2000/XP, хотя, так как Windows 9х не поддерживает Unicode, приложения типа Notepad не смогут понять файл Unicode на этих платформах (Если загрузить пример с web-сайта издательства Wrox Press, то можно попробовать это сделать.) Однако, если попробовать вывести файл снова с помощью предыдущего примера ReadBinaryFile
, то разница будет заметна немедленно, как на следующем экране. Два начальных файла указывают, что файл имеет формат Unicode, и поэтому мы видим, что каждый символ представлен двумя байтами. Этот последний факт вполне очевиден, поскольку старший байт каждого символа в данном конкретном файле равен нулю, поэтому каждый второй байт в этом файле выводится теперь как x00:
Чтение и запись в реестр
Во всех версиях Windows, начиная с Windows 95, реестр был центральным репозиторием всех конфигурационных данных, связанных с настройкой Windows, предпочтениями пользователя и установленным программным обеспечением и устройствами. Почти все коммерческое программное обеспечение сегодня использует реестр для хранения информации о себе, и компоненты COM должны помещать информацию о себе в реестр, чтобы клиент смог их вызвать. Платформа .NET и сопровождающая ее концепция о нулевом влиянии установки слегка уменьшили значение реестра для приложений в том смысле, что сборки являются полностью самодостаточными, поэтому никакая информация об определенных сборках не должна помещаться в реестр для сборок общего использования.
Тот факт, что приложения могут теперь устанавливаться с помощью программы установки Windows также освобождает разработчика от некоторых прямых манипуляций с реестром, которые обычно были связаны с установкой приложений. Однако, несмотря на это, при распространении любого законченного приложения вполне вероятно, что это приложение будет использовать реестр для хранения информации о своей конфигурации. Если приложение появляется в диалоговом окне Add/Remove Programs в панели управления, то создается соответствующая запись в реестре.
Как и можно было ожидать от такой всеобъемлющей библиотеки, как библиотека .NET, она содержит классы, которые предоставляют доступ к реестру. Имеются два класса, связанных с реестром, и оба находятся в пространстве имен Microsoft.Win32
. Это классы Registry
и RegistryKey
. Прежде чем рассматривать их, кратко разберем структуру самого реестра.
Реестр
Реестр имеет иерархическую структуру, очень похожую на файловую систему. Обычно просмотр или изменение содержимого реестра выполняется с помощью одной из двух утилит — regedit
или regedt32
. regedit
стандартно поставляется со всеми версиями Windows, начиная с Windows 95. Утилита regedt32
поставляется с Windows NT и Windows 2000 — она менее дружественна пользователю, чем regedit
, но разрешает доступ к данным безопасности, которые regedit
не может видеть. Здесь будет использоваться regedit
, которую можно запустить, вводя regedit
в диалоговом окне Run… или командной строке.
При первом запуске regedit
появится примерно следующее изображение:
Regedit
имеет интерфейс пользователя в стиле представлений дерева/списка, аналогичный Проводнику Windows, который соответствует иерархической структуре самого реестра. Однако, как мы скоро увидим, существуют некоторые различия.
В файловой системе узлами самого верхнего уровня можно считать разделы диска C:, D: и т.д. В реестре эквивалентом разделу является улей реестра. Невозможно изменить