Исключение десериализации двоичного средства форматирования

Я использую BinaryFormatter для сериализации и десериализации. Из-за некоторых требований мне нужно изменить имя пространства имен и имя класса.

В обоих случаях - либо я меняю имя пространства имен, либо меняю имя класса, я получаю исключение сериализации.

Есть ли способ решить эту проблему?


person Pankaj Kherodiya    schedule 08.02.2019    source источник
comment
Не могли бы вы показать нам исключение и код?   -  person kara    schedule 08.02.2019
comment
BinaryFormatter очень хрупок, когда дело доходит до любого типа управления версиями, особенно когда речь идет о полном имени типов (сборка, пространство имен, имя типа и т. д.), а также во многих других факторах. . Он действительно ненавидит подобные вещи. Можно ли вообще удаленно изменить сериализатор? Буквально все остальное было бы лучше, чем BinaryFormattter. Извините, но BinaryFormatter рекомендуется в очень небольшом, но реальном наборе сценариев; однако в большинстве случаев это просто будет причинять вам боль снова и снова.   -  person Marc Gravell    schedule 08.02.2019
comment
Чтобы преобразовать из одного формата в другой, вам нужно поместить в свое приложение как старое пространство имен/класс, так и новое пространство имен/класс. Преобразование записи для перехода от старого к новому. Чтобы отслеживать старые и новые файлы, я бы добавил к имени файла номер версии, чтобы вы могли проверить, работаете ли вы со старым или новым форматом.   -  person jdweng    schedule 08.02.2019
comment
из-за требований проекта мне нужно только изменить имя моего пространства имен и имя класса, а остальная часть структуры одинакова в обеих версиях. Можем ли мы поддержать это поведение.   -  person Pankaj Kherodiya    schedule 08.02.2019


Ответы (1)


Вы можете сделать это, написав свой собственный SerializationBinder, т.е.

class MyCustomBinder : SerializationBinder
{
    public override void BindToName(Type serializedType, out string assemblyName, out string typeName)
    {
        // TODO: turn a Type into a pair of strings
    }
    public override Type BindToType(string assemblyName, string typeName)
    {
        // TODO: turn a pair of strings into a Type
    }
}

Затем вы должны указать .Binder в экземпляре BinaryFormatter, и он должен работать. Вам нужно будет выяснить, какими были старые assemblyName/typeName и т. д., конечно, и убедиться, что они ведут себя как таковые в обоих направлениях.

Однако... и я не могу не подчеркнуть этого достаточно: если вы столкнулись с этой проблемой, BinaryFormatter, вероятно, просто плохой выбор сериализатора. Существует множество альтернативных сериализаторов, которые справились бы с задачей гораздо лучше, будучи более эффективными и более удобными для рефакторинга. Пожалуйста, обратите внимание на изменение сериализатора.

person Marc Gravell    schedule 08.02.2019