Почему сериализация double [] не работает в WinCE?
4 Nikodemus [2012-02-23 13:41:00]
У меня есть объект с (де-) сериализует его конфигурацию через system.xml.serializer
Конфигурация в классе выглядит следующим образом:
public struct Phase
{
public Int16 Trafo;
public KorrekturWerte Spannung;
public KorrekturWerte Strom;
[XmlArray("Min")]
public double[] Min;
[XmlArray("Max")]
public double[] Max;
public bool CheckThis;
}
public class ParameterHardware
{
public string WAGOId = "00:30:DE:05:33:CB";
public Byte Phasen = 0x07;
public Phase L1;
public Phase L2;
public Phase L3;
}
(De-) Сериализация этого в WindowsXP-системе работает очень хорошо, но в Windows CE Min/Max-Array просто рушится после дезактивации и затем ресериализуется ( "CheckThis" был помещен туда как тест и следует после сериализации значений "Strom" ). Поскольку KorrekturWerte снова является структурой, глубина не может быть проблемой. [XmlArray...] не было в моей первой версии, это просто из другого теста.
Edit:
-
Проблема не (только) в сериализации. Пытаюсь получить доступ к Min [...] Я получаю ошибку нулевой ссылки.
-
Возможно, это не ясно: у меня есть сериализация класса, который содержит все значения. Уничтожьте его, чтобы инициализировать класс, а затем повторите его как проверку отладки. Теперь поля отсутствуют. (Исходный файл был сериализован в XP, где он работает правильно)
-
Смена двойного [] на список не помогает. (Тот же результат)
-
xml файлы: Оригинал:
00: 30: DE: 05: 53: 65 1 50 -0,2 1 0,004 0,994 0 0 0 0 0 500 32 15000 15000 1 правда 50 0 1 0 1 0 0 0 0 0 500 32 15000 15000 1 50 0 1 0 1 0 0 0 0 0 500 32 15000 15000 1
Повторная инициализация (извините, CE сериализуется в одной строке):
<?xml version="1.0" encoding="utf-8"?><ClassTest_FCT_Extern xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"><Hardware><WAGOId>00:30:DE:05:53:65</WAGOId><Phasen>1</Phasen><L1><Trafo>50</Trafo><Spannung><Offset>-0.2</Offset><Steigung>1</Steigung></Spannung><Strom><Offset>0.004</Offset><Steigung>0.994</Steigung></Strom><CheckThis>true</CheckThis></L1><L2><Trafo>50</Trafo><Spannung><Offset>0</Offset><Steigung>1</Steigung></Spannung><Strom><Offset>0</Offset><Steigung>1</Steigung></Strom><CheckThis>false</CheckThis></L2><L3><Trafo>50</Trafo><Spannung><Offset>0</Offset><Steigung>1</Steigung></Spannung><Strom><Offset>0</Offset><Steigung>1</Steigung></Strom><CheckThis>false</CheckThis></L3></ClassTest_FCT_Extern>
-
Извините за то, что вы нанесли все кусочки ломтиками. Вот код сериализации (с использованием System.Xml.Serialization;)
try { fstream = new FileStream(filepath, FileMode.Open, FileAccess.Read); reader = new XmlTextReader(fstream); serializer = new XmlSerializer(typeof(T)); retobj = (T)serializer.Deserialize(reader); } catch (Exception e) { Debug("Serialization: "+e.ToString()); retobj = Activator.CreateInstance<T>(); }
Отладка не вызывается, поэтому ошибок не возникает.
- Версия .net 2.0.
c# .net windows-ce xml-serialization
2 ответа
5 Решение BlueM [2012-02-23 13:52:00]
Ваш массив min/max должен быть инициализирован с помощью new double[]
или его нулевого значения, и у вас есть исключения nullREF и отсутствующие поля. Нулевые значения не сериализованы и отсутствуют.
Edit2:
Похоже, что существует проблема десериализации массивов/списков для вас. Пожалуйста, сделайте имена тегов элементов массива более откровенными:
[XmlArray("Min")]
[XmlArrayItem("Value")]
public double[] Min;
[XmlArray("Max")]
[XmlArrayItem("Value")]
public double[] Max;
и попробуйте, если это вам поможет.
Edit3
Из того, что вы описали в нашей дискуссии и чате, вы столкнулись с реальной ошибкой в .NET Compact Framework 2.0.
Таким образом, лучше всего использовать пользовательский Deserializer под CE, если вы не можете обновить Framework.
Были также некоторые другие ошибки, описанные в CE здесь.
3 Nikodemus [2012-02-23 18:19:00]
Поиск других (рабочих) решений, я, наконец, обнаружил разницу между ними и моим подходом. У меня был открытый двойник [], а затем в некоторых тестах публичный список. Все остальные решения имели приватный List < > , а затем публичный getter. (Этого достаточно для List < > для сериализации). Таким образом, меняя свою структуру, все работает отлично:
public class Phase
{
public Int16 Trafo = 50;
public KorrekturWerte Spannung = new KorrekturWerte() { Offset = 0, Steigung = 1 };
public KorrekturWerte Strom = new KorrekturWerte() { Offset = 0, Steigung = 1 };
private List<double> m_Min = new List<double>();
private List<double> m_Max = new List<double>();
public List<double> Min { get { return m_Min; } }
public List<double> Max { get { return m_Max; } }
//public double[] Default;
}