Не помечено как сериализуемая ошибка при сериализации класса - программирование
Подтвердить что ты не робот

Не помечено как сериализуемая ошибка при сериализации класса

Я сериализую структуру, используя BinaryFormatter, используя этот код:

private void SerializeObject(string filename, SerializableStructure objectToSerialize)
{
    Stream stream = File.Open(filename, FileMode.Create);
    BinaryFormatter bFormatter = new BinaryFormatter();
    bFormatter.Serialize(stream, objectToSerialize);
    stream.Close();
}

Какая objectToSerialize - моя структура, я вызываю эту функцию следующим образом:

SerializableStructure s = new SerializableStructure();
s.NN = NN;
s.SubNNs = SubNNs;
s.inputs = inputs;
SerializeObject(Application.StartupPath + "\\Save\\" + txtSave.Text + ".bin", s);

Какой SerializableStructure, а тип NN, SubNNs и входы сериализуемы. (входы содержат некоторые Points, Rectangles и общие списки).

Теперь, когда я запускаю свой код, мне присваивается эта ошибка:

Введите "MainProject.Main" в Assembly "MainProject, Version = 1.0.0.0, Culture = neutral, PublicKeyToken = null" не помечен как сериализуемый.

Почему мне дана эта ошибка? Главная моя форма, и эти переменные расположены в моей форме.

Я успешно сериализовал тип NN с MemoryStream и VB.NET, но я не знаю, почему я получаю эту ошибку?

Вот определение моих структур:

SerializableStructure:

[Serializable()]
public class SerializableStructure
{
    public List<Inputs> inputs = new List<Inputs>();
    public NeuralNetwork NN;
    public NeuralNetwork[] SubNNs;
}

Входы:

[Serializable()]
public class Inputs
{
    public string XPath { get; set; }
    public string YPath { get; set; }
    public string ImagePath { get; set; }
    public string CharName { get; set; }
    public string CharBaseName { get; set; }
    public List<double> x { get; set; }
    public List<double> y { get; set; }
    public List<double> DotsX { get; set; }
    public List<double> DotsY { get; set; }
    public List<Point> GravityCenters { get; set; }
    public List<Rectangle> Bounds { get; set; }

    public override string ToString()
    {
        return CharName;
    }

    public Inputs(string xPath, string yPath, string imagePath, string charName, string charBaseName)
    {
        XPath = xPath;
        YPath = yPath;
        ImagePath = imagePath;
        CharName = charName;
        CharBaseName = charBaseName;
        x = new List<double>();
        y = new List<double>();
        GravityCenters = new List<Point>();
        Bounds = new List<Rectangle>();
    }
}

Также NN - очень большая структура (!).

4b9b3361

Ответ 1

Это почти всегда означает, что у вас есть событие (или другой делегат - возможно, обратный вызов) где-то в вашей объектной модели, который пытается сериализоваться. Добавьте [NonSerialized] в любые поля поддержки событий. Если вы используете полевое событие (наиболее вероятный вид), это:

[field:NonSerialized]
public event SomeDelegateType SomeEventName;

Альтернативно: большинство других сериализаторов не смотрят на события/делегаты и не обеспечивают лучшую совместимость версий. Переключение на XmlSerializer, JavaScriptSerializer, DataContractSerializer или protobuf-net (всего 4 примера) также решит это простым подходом к тому, чтобы не пытаться это сделать (вы почти никогда не намерены рассматривать события как часть DTO).

Ответ 2

Проблема в том, что вы пытаетесь сериализовать класс, полученный из формы. Класс Form принципиально неэриализуем. Он имеет огромное количество внутреннего состояния, которое сильно зависит от времени выполнения. Это начинается с очевидного свойства, такого как Handle, значение, которое всегда отличается. Менее очевидны такие свойства, как Размер, в зависимости от пользовательских настроек, таких как размер шрифта для заголовка окна. Завершает весь текст, местоположение и размеры элементов управления, они подлежат локализации. Вероятность того, что сериализованный объект Form может быть должным образом десериализован в любое время для создания точного клона формы, равна нулю.

Microsoft не делала никаких костей, когда они писали код, они просто опускали атрибут [Serializable] из объявления класса. Вот почему вы получаете исключение.

Вам нужно будет опуститься ниже, написать свой собственный класс, чтобы захватить ваше состояние формы. И придать ему атрибут. Вам нужно будет написать кучу кода, который сопоставляет форму и свойства управления объекту этого класса, назад и вперед.