PDA

View Full Version : سوال: ناهمخوانی شی منتج شده از Desrialize کردن فایل Xml با آبجکت اولیه که فایل Xml از روی آن Serialize شده



pooya1072
یک شنبه 29 خرداد 1401, 23:54 عصر
سلام
فرض کنید کلاسی داریم به نام CourseList :


namespace Project
{
[Serializable]
public class CourseList
{
[XmlElement("Courses",IsNullable =true))]
public List<string> Courses { get; set; }
}
}

درون متد Main یک نمونه از این کلاس میسازیم و نمونه را درون یک فایل Xml سریال می کنیم . (خاصیت Courses را new نمیکنم) :




namespace Project
{
class Program
{
static void Main(string[] args)
{

CourseList SerializedCourses = new CourseList();
XmlSerializer serializer = new XmlSerializer(typeof(CourseList));
TextWriter writer = new StreamWriter("ex.xml");
serializer.Serialize(writer, SerializedCourses );
writer.Close();

Console.ReadKey();

}
}
}

فایل Xml خروجی به شکل زیر است :


<?xml version="1.0" encoding="utf-8"?>
<CourseList xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" />
حالا همین فایل xml رو Deserialize می کنیم و در آبجکت DeserializedCourses قرار می دهیم :



CourseList DeserializedCourses;
FileStream fs = new FileStream("ex.xml", FileMode.Open);
DeserializedCourses = (CourseList)serializer.Deserialize(fs);

در شی SerializedCourses , فیلد Courses به درستی null است .چون اصلا مقدار دهی و نمونه سازی نشده
ولی مشکل اینجاست که در شی DeserializedCourses , فیلد Courses مقدارش null نیست و یرای خاصیت Courses نمونه ساخته شده و من متوجه نمیشم که چطور.

این هم عکس از پنجره Watch محیط Debugging :

153849
ممنون میشم نظرتون رو بگید.

Mahmoud.Afrad
دوشنبه 30 خرداد 1401, 01:39 صبح
IsNullable را برای پراپرتی هایی که میتونن null باشند، ست کنید.
https://docs.microsoft.com/en-us/dotnet/api/system.xml.serialization.xmlelementattribute.isnul lable

pooya1072
دوشنبه 30 خرداد 1401, 02:02 صبح
IsNullable را برای پراپرتی هایی که میتونن null باشند، ست کنید.
https://docs.microsoft.com/en-us/dotnet/api/system.xml.serialization.xmlelementattribute.isnul lable
سلام و تشکر
من IsNullable رو برای هر دو حالت هم true هم false ست کردم. هیچ تفاوتی نداره.
در هر حال نمونه سازی میشه

Mahmoud.Afrad
سه شنبه 31 خرداد 1401, 03:46 صبح
خروجی xml در این دو حالت تفاوتی هم داره یا نه؟

pooya1072
سه شنبه 31 خرداد 1401, 06:21 صبح
خروجی xml در این دو حالت تفاوتی هم داره یا نه؟
خروجی xml هر دو‌ یکسان است :

<?xml version="1.0" encoding="utf-8"?>
<CourseList xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" />

مهدی کرامتی
سه شنبه 31 خرداد 1401, 09:10 صبح
اجبار خاصی وجود داره که از فرمت Xml برای پروسه Serialization/DeSerialization استفاده می کنید؟

استفاده از فرمت JSON خیلی راحت تره، ابزارهای Serialization اش هم خیلی بروزتر و مدرن تر هستند، حجم خروجی سریالایز شده اش هم کمتره، و در صورت نیاز به استفاده از آبجکت سریالایز شده در تکنولوژی هایی غیر مبدا، خیلی راحت تر خواهید بود.

pooya1072
سه شنبه 31 خرداد 1401, 16:26 عصر
اجبار خاصی وجود داره که از فرمت Xml برای پروسه Serialization/DeSerialization استفاده می کنید؟

استفاده از فرمت JSON خیلی راحت تره، ابزارهای Serialization اش هم خیلی بروزتر و مدرن تر هستند، حجم خروجی سریالایز شده اش هم کمتره، و در صورت نیاز به استفاده از آبجکت سریالایز شده در تکنولوژی هایی غیر مبدا، خیلی راحت تر خواهید بود.
اجبار خاصی نیست واقعا
فقط این قضیه ذهنم رو مشغول کرده بود
فقط یه وسواس فکری شده برام .... در هر حال ممنون
توی سایت StackOverFlow م سوال رو مطرح کردم ولی اونجا هم جوابی نگرفتم
C#‎‎‎ - The Deserialized Object is different from the Serialized Object with the same class - Stack Overflow (https://stackoverflow.com/questions/72659002/the-deserialized-object-is-different-from-the-serialized-object-with-the-same-cl)

Mahmoud.Afrad
چهارشنبه 01 تیر 1401, 04:14 صبح
با معرفی نوع داده , isnullable هم کار کرد

[XmlElement(
Type = typeof(List<string>) ,
IsNullable = true)
]

pooya1072
چهارشنبه 01 تیر 1401, 07:19 صبح
با معرفی نوع داده , isnullable هم کار کرد

[XmlElement(
Type = typeof(List<string>) ,
IsNullable = true)
]


سلام و تشکر بابت پیگیری شما
کلاس را طبق راهنمایی شما تغییر دادم ولی همچنان فیلد Courses شی DeserializedCourses که از فایل ex.xml استخراج شده مقدارش null نمیشه . در صورتی که فیلد Courses شی SerializedCourses که فایل ex.xml از سریال کردن اون ایجاد شده مقدارش null



namespace TreeProject
{
[XmlRoot(ElementName = "CourseList")]
public class CourseList
{
[XmlElement(Type =typeof(List<string>),IsNullable =true)]
public List<string> Courses { get; set; }
}
}

ShayanFiroozi
پنج شنبه 02 تیر 1401, 14:54 عصر
سلام ،

از کتابخانه Protobuf استفاده کنین. چندین برابر از Serialization مایکروسافت و JSON سریعتر و قوی تره.

از طریق دستور زیر در Package Manager میتونین Protobuf رو به پروژتون اضافه کنین.

Install-Package protobuf-net




[ProtoContract]
public class CourseList
{
[ProtoMember(1)]
public List<string> Courses { get; set; }
}


public byte[] Serialize(CourseList input)
{
using (MemoryStream memoryStream = new MemoryStream())
{
Serializer.Serialize(memoryStream, input);
return memoryStream.ToArray();
}
}


public CourseList DeSerialize(byte[] data)
{
return Serializer.Deserialize<CourseList>(new MemoryStream(data));
}




چند نکته :



تقریبا تمامی ابزار های Serialization با Dictionary ها مشکل دارن ، پس از Dictionary ها استفاده نکنین.
خروجی Protobuf از نوع byte[] هستش یعنی داده واقعی که میتونین توی فایل ذخیره کنین و حتی همونو روی شبکه Transfer کنین ولی خروجی JSON ها Text هستش که این خیلی میتونه دردسر ساز بشه.
عملکرد Protobuf خیلی سریعتر از Serialization های مایکروسافته ، ضمنا Binary Serialization منسوخ شده (کلیک کنین (https://docs.microsoft.com/en-us/dotnet/core/compatibility/core-libraries/5.0/binaryformatter-serialization-obsolete))





153873



برای اطلاعات بیشتر کلیک کنین (https://dotnetcoretutorials.com/2022/01/18/protobuf-in-c-net-part-4-performance-comparisons/)