Вы можете найти рассылки сходной тематики в Каталоге рассылок.
Данная рассылка задумывается как аналог премодерируемой конференции.
Здесь мы, люди изучающие и использующие платформу .NET,
сможем обменяться своими находками и идеями.
Присылайте ваши стать и вопросы на адрес
level3@mail.ru.
Они будут помещены в рассылку с указанием имени и (по желанию) адреса
автора.
На письма с очень часто задаваемыми вопросами я постараюсь ответить,
не помещая их в рассылку.
Таким образом, надеюсь, что материалы будут интересными для Вас.
Сериализация - это процесс преобразования графа объектов в последовательность байтов. Полученная последовательность байтов может быть перенесена через пространство и/или время и восстановлена обратно (Deserialization) в граф объектов.
В CLR поддержка сериализации производиться классами из пространства имен System.Serialization и средой выполнения (runtime system)
Компилятору и среде выполнения известно, где находятся данные объекта. Это позволяет написать обобщенную библиотеку для сохранения любых (ну почти) объектов и тогда становится не нужно писать в каждом объекте код для сохранения данных объекта.
При сериализации система поддержки решает следующие задачи:
1) преобразование ссылок на объекты во что-либо, т.к. ссылки - это адреса
расположения объектов в памяти и они не имеют смысла в другом контексте.
Т.е. при следующем запуске программы объекты будут располагаться в памяти
по-другому
и их адреса будут другими.
Можно пронумеровать все объекты, которые будут сохранены и записывать
вместо адресов полученные номера.
2) следить за сохранением "неповторимости" ;) объекта
Порядок, в котором будут пронумерованы объекты, не имеет значения. Важно,
чтобы номера были уникальными.
Алгоритму, который обрабатывает объекты по одному, требуется способ
определять,
какие объекты были пронумерованы, а какие нет. Для этого алгоритм может
поддерживать внутренний список. Если же не запоминать, какие объекты были
сохранены, а какие - нет, то может получиться так, что один объект
будет сохранен два раза. При считывании это приведет к тому, что вместо
одного исходного объекта будет создано два.
Есть два способа записывать объекты.
В одном случае все данные объекта располагаются близко друг к другу, в
другом
объект вписывается внутрь сославшегося на него объекта вместо ссылки.
В .NET выбран первый.
Выходной поток может быть представлен в двоичном виде и в виде XML (SOAP).
Можно написать свой класс, который будет форматировать выходной поток так, как нужно (например, в текстовом виде. А можно сохранить в XML-виде и затем преобразовать в текст).
using System; using System.IO; using System.Collections; using System.Serialization; using System.Serialization.Formatters.Binary; class SerializeExample { public static void Main(String[] args) { // create the object graph ArrayList l = new ArrayList(); for (int x=0; x< 100; x++) { l.Add (x); } // create the filestream FileStream s = File.Create("foo.bin"); // create the BinaryFormatter BinaryFormatter b = new BinaryFormatter(); // serialize the graph to the stream b.Serialize(s, l); } // end main } // end class class DeSerialize { public static void Main(String[] args) { // open the filestream FileStream s = File.Open("foo.bin"); // create the formatter BinaryFormatter b = new BinaryFormatter(); // deserialize ArrayList p = (ArrayList) b.Deserialize(s); // use the new object graph Console.WriteLine(p.ToString()); } // end Main } // end Class DeSerialize
В качестве потоков можно использовать FileStream, MemoryStream и NetStream.
public interface IFormatter: { // Properties SerializationBinder Binder { get; set; } StreamingContext Context { get; set; } ISurrogateSelector SurrogateSelector { get; set; } //Methods object Deserialize(Stream serializationStream); void Serialize(Stream serializationStream, object graph); }
При необходимости можно написать специальную версию любого из этих объектов.
Например специальный Formatter может приписывать заголовок файла.
(для чего еще)?
Это может быть нужно например в тех случаях, когда часть полей вычисляется.
(хотя почему бы их тоже не записать и
потом считать?)
Интересно заметить, что в общем случае значения полей объекта узнаются при помощи Reflection, а оно не гарантирует, что значения полей объекта будут возвращаться в том порядке, в котором хранятся метаданные о них.
Для того, чтобы система сохраняла объект, его класс
должен быть помечен атрибутом [Serializable]
Атрибут [NotSerialized] является аналогом ключевому слову transient
из java.
Если некоторый объект должен сохраняться не как все, то нужно реализовать интерфейс ISerializable.
В этом интерфейсе есть две функции - GetObjectData и конструктор.
Функция GetObjectData в момент сохранения объекта
должна заполнить объект SerializationInfo.
SerializationInfo хранит тип сохраняемого объекта и массив пар "имя поля" -
"значение".
Далее SerializationInfo передается в объект класса Formatter
При восстановлении объекта из потока конструктор не будет вызван до тех пор, пока не будут собраны все необходимые данные (т.е. значения полей и ссылок на другие объекты). Однако не дается гарантии, что соседние объекты проинициализированы (т.е. нельзя вызывать из методы). Это почти очевидно, достаточно представить себе сохранение и восстановление кольца (цикла) из объектов.
Если же для восстановления состяния требуются данные из других объектов,
то можно реализовать интерфейс IDeserializationEventListener. Метод этого
интерфейса
будет вызван для каждого зарегистрировавшегося объекта сразу
же после восстановления всего графа.
В качестве примера стоит привести объект с хеш-таблицей. Для того, чтобы
реконструировать
такую таблицу нужно чтобы все объекты, входящие в нее, уже были созданы.
Если реализовывать Object->Relational bridge, то можно ли воспользоваться
имеющимся механизмом сериализации написав свой formatter?
Понятно, что в общем случае - нет, т.к. тогда придется сохранять
весь граф объектов целиком. А если реализовывать bridge с нуля,
но можно сохранять/считывать только нужные объекты, а вместо несчитанных
вставлять заглушки.
-----Original Message----- Sent: Friday, August 31, 2001 3:19 PM To: level3@mail.ru Subject: Вопрос ? Сергей, добрый день! С интересом стал читать Вашу рассылку. Но есть один маленький вопрос: - Что необходимо для выполнения программы на С#, т.е. потребуется ли дополнительная среда разработки (типа VC++) или можно обойтись текстовым редактором? С уважением и наилучшими пожеланиями, Алексей К. ---------Алексей,
можно обойтись текстовым редактором и Framework'ом (~20Mb в архиве), но лучше добыть VS.NET Beta2 на пяти дисках (professional версия распространяется на пяти компакт-дисках, но один из дисков - патчи к операционным системам).
В Visual Studio очень удобный редактор, который специально предназначен для работы с текстом на C# (он умеет сворачивать текст, чего мне очень не хватало в JBuilder 3.5), кроме того, там есть редактор форм, многочисленные заготовки, справка, в конце концов.
Удачи!
(лежит в %windir%\Microsoft.NET\Framework)
Итак: для выполнения программы на C# требуется Microsoft .NET Framework.
Это пакет включает в себя .dll-файлы,
в которых содержаться различные стандартные модули а так же компиляторы.
Утилиты, входящие в состав Framework:
(лежит в %Program Files%\Microsoft.NET\FrameworkSDK)
Еще бывает Microsoft Framework SDK. Framework SDK не установится, если версия Explorer'а < 6.0, поэтому он при установке сначала предложит обновить Explorer.
Включает в себя IDE, CrystalReports.NET, Platform SDK и MSDN.NET
К сожалению, у меня здесь MSDN за апрель 2001, поэтому много чего не хватает. Если я чего не заметил, напишите.
С уважением и наилучшими пожеланиями,
Сергей Радкевич.
BODY >
HTML >
http://subscribe.ru/
E-mail: ask@subscribe.ru |
Отписаться
Убрать рекламу | Рейтингуется SpyLog |
В избранное | ||