2010-03-20 3 views
2

Я создал приложение для телефонной книги, и он отлично работает после некоторого времени, когда мне понравилось сделать обновление для моего приложения, и я начал с нуля, я не наследовал его от своего старого класса, и я тоже добился успеха, мой запрос «Я хочу, чтобы перенести свои контакты из старого приложения в новой» , поэтому я сделал класс адаптера по этой причине в моем новом приложении с помощью следующего кодаПроблема с сериализацией

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.IO; 
using System.Windows.Forms; 
using System.Runtime.Serialization; 
using System.Runtime.Serialization.Formatters.Binary; 

namespace PhoneBook 
{ 
    class Adapter 
    { 
     PhoneRecord PhRecord; //the new application object 
     CTeleRecord TelRecord; //the old application object 
     string fileName; 

    public Adapter(string filename) 
    { 
     fileName = filename; 
    } 

    public void convert() 
    { 

     PhRecord = new PhoneRecord(); 
     TelRecord = new CTeleRecord(); 

     FileStream OpFileSt = new FileStream(fileName, FileMode.Open,FileAccess.Read); 


     BinaryFormatter readBin = new BinaryFormatter(); 



     for (; ;) 
     { 
      try 
      { 
       TelRecord.ResetTheObject(); 

       TelRecord = (CTeleRecord)readBin.Deserialize(OpFileSt); 

       PhRecord.SetName = TelRecord.GetName; 
       PhRecord.SetHomeNumber = TelRecord.GetHomeNumber; 
       PhRecord.SetMobileNumber = TelRecord.GetMobileNumber; 
       PhRecord.SetWorkNumber = TelRecord.GetWorkNumber; 
       PhRecord.SetSpecialNumber = TelRecord.GetSpecialNumber; 
       PhRecord.SetEmail = TelRecord.GetEmail; 
       PhRecord.SetNotes = TelRecord.GetNotes; 
       PhBookContainer.phBookItems.Add(PhRecord); 


      } 
      catch (IOException xxx) 
      { 
       MessageBox.Show(xxx.Message); 


      } 
      catch (ArgumentException tt) 
      { 
       MessageBox.Show(tt.Message); 
      } 
      //if end of file is reached 
      catch (SerializationException x) 
      { 
       MessageBox.Show(x.Message + x.Source); 
       break; 
      } 

     } 
     OpFileSt.Close(); 

     PhBookContainer.Save(@"d:\MyPhBook.pbf"); 

     } 

    } 
} 

проблемы, когда я пытаюсь для чтения файла, обработанного моим старым приложением, я получаю исключение сериализации с этим сообщением «Unalel, чтобы найти сборку» PhoneBook, Version = 1. 0.0.0, Культура = нейтраль, PublicK eyToken = null "

и источником исключения является mscorlib.

, когда я читаю один и тот же файл с моим старым приложением (что является источником файла) У меня нет проблем, и я не знаю, что делать, чтобы сделать мой класс адаптера.

ответ

2

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

Проблема в том, что, хотя оба класса могут казаться идентичными, они не потому, что они находятся в разных сборках.

Рекомендуемый способ - всегда ставить сериализуемые классы в библиотеке классов. Затем в вашей ситуации V2.0 вашего приложения может ссылаться на сборку V1.0, а затем вы можете десериализовать объекты.

Если ваши классы V1.0 не находятся в библиотеке классов (например, они встроены в исполняемый файл), вы можете создавать свои классы V2.0 в библиотеке классов и добавлять функциональные возможности в свое приложение V1.0 для преобразования классов в классы V2.0.

Опубликовать любые вопросы, которые могут возникнуть как комментарии.

Надеюсь, это поможет.

0

Как указано выше, файл содержит полное имя сборки вашего класса, которое было изменено в новом проекте. Если вы сборка, имя и пространств имен вашего класса матча, вы можете установить формат Assembly, чтобы просто на форматере:

BinaryFormatter.AssemblyFormat = FormatterAssemblyStyle.Simple; 

Этого использование LoadWithPartialName когда форматировщик пытается загрузить этот тип. См. MSDN для получения дополнительной информации.

Вы также можете написать serialization binder для устранения разногласий.

+0

спасибо за всех –

+0

Я попробую ответить 2, так как h'm C# beginner –

1

BinaryFormatter не очень толерантен к изменениям сборки. Я давно пришел к выводу, что это нормально (просто) для транспорта, но не подходит для любого типа хранилища - это just too brittle.

Короче говоря, я хотел бы использовать другой сериалайзер - но на контрактной основе, а не на основе типа (так что любой тип с тем же cnotract может обмениваться данными):

  • во многих случаях XmlSerializer будет делать; он имеет некоторые ограничения (публичные типы и члены), но он работает обычно
  • с. NET 3.0, DataContractSerializer полезно
  • или если вы хотите что-то за пределами кода LIBS, protobuf-net очень быстро и эффективен

Из них только DataContractSerializer будет в настоящее время поддержки режим «график» (а не дерева) ,

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

Смежные вопросы