Исключения при использовании BinaryFormatter для десериализации моих сериализованных данных - PullRequest
4 голосов
/ 17 декабря 2010

Я использую BinaryFormatter и MemoryStream, чтобы сериализовать объект, а затем сохранить его в базе данных в виде двоичного двоичного объекта.Затем я извлекаю данные из базы данных и десериализую, используя двоичный форматер и поток памяти.

Однако, когда я пытаюсь десериализовать объект, я часто получаю исключения.В частности, 'an object with the same key already exists' или 'cannot convert string to int64'

У кого-нибудь есть идеи относительно того, почему десериализация выпадает?или как узнать, какой объект словаря испытывает проблемы?

Мои функции сериализации следуют ...

private byte[] SerializeUserData(UserData ud)
{
    byte[] data = null;
    using (MemoryStream ms = new MemoryStream())
    {
        ms.Seek(0, SeekOrigin.Begin);
        BinaryFormatter bf = new BinaryFormatter();
        bf.Serialize(ms, ud);
        data = ms.ToArray();
    }
    return data;
}

private UserData Deserialize()
{
    UserData ud = null;
    using (MemoryStream ms = new MemoryStream(mSession.BinarySession))
    {
        BinaryFormatter bf = new BinaryFormatter();
        ud = bf.Deserialize(ms) as UserData;
    }
    return ud; 
}

Класс UserData немного монстр, но помечен как [serializable] и все классы в его дереве объектов также помечены как [serializable].Часть этого класса следует:

[Serializable]
public class UserData
{
        public UserData() { Clear(); }
        public Guid Id { get; set; }

        public Account Account { get; set; }
        public List<Account> OldAccounts{ get; set; }

        public void Clear()
        {
          Account = null;
          OldAccounts = new List<Account>();
          Id = Guid.NewGuid();
        }
}

1 Ответ

5 голосов
/ 17 декабря 2010

Я не пробовал это в последних версиях фреймворка, но думаю, что эмпирическое правило, вероятно, все еще хорошо, не используйте BinaryFormatter с автоматическими свойствами.

Проблема в том, что BinaryFormatter использует поля поддержки, а не свойства для выполнения сериализации / десериализации. В случае авто свойств, поле поддержки создается во время компиляции. И это не гарантируется быть одинаковым каждый раз. Это может означать, что вы десериализовали свой объект и не вернули точно то, что вставили.

Подробнее читайте здесь: Автоматические свойства и двоичный формат

...