当前位置: 动力学知识库 > 问答 > 编程问答 >

c# - Why can I no longer deserialize this data?

问题描述:

I am using the following code to serialize some data and save it to file:

 MemoryStream stream = new MemoryStream();

DataContractJsonSerializer serializer = new DataContractJsonSerializer((typeof(Item)));

Item item = ((Item)list.SelectedItems[0].Tag);

serializer.WriteObject(stream, item);

var filepath = Program.appDataPath + list.SelectedItems[0].Group.Name + ".group";

stream.Position = 0;

using (FileStream fileStream = new FileStream(filepath, FileMode.Create))

{

stream.WriteTo(fileStream);

}

And later on, I'm trying to read back that data from file and insert it into ListView:

 private void OpenFiles()

{

// DEBUG ONLY:

// Read into memorystream and filestream.

Console.WriteLine("Attempeting to open note.");

bool canLoad = false;

foreach (string file in Directory.GetFiles(Program.appDataPath))

{

if (file.EndsWith(".group"))

{

MemoryStream stream = new MemoryStream();

DataContractJsonSerializer serializer =

new DataContractJsonSerializer(

typeof(

List<Item>

)

);

using (FileStream fileStream =

new FileStream(

file,

FileMode.Open)

)

{

fileStream.CopyTo(stream);

}

stream.Position = 0;

//List<Withdrawal> tempWithList = new List<Withdrawal>();

foreach (Item item in (List<Item>)serializer.ReadObject(stream))

{

Console.WriteLine(item.Title + " " + item.Group.Name);

Item.Items.Add(item);

}

//Console.WriteLine("Got file \{file}");

//if (file.EndsWith(".group"))

//{

// Console.WriteLine("File is a group.");

// MemoryStream stream = new MemoryStream();

// DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(List<Item>));

// using (FileStream fileStream = new FileStream(file, FileMode.Open))

// {

// fileStream.CopyTo(stream);

// }

// Console.WriteLine("Got stream");

// stream.Position = 0;

// try

// {

// Item.Items = (List<Item>)serializer.ReadObject(stream);

// Console.WriteLine("WTF?");

// }

// catch(Exception exception)

// {

// Console.WriteLine(exception.Message);

// }

// Console.WriteLine(Item.Items.Count);

// canLoad = true;

//}

//else Console.WriteLine("File is not a group.");

}

if (canLoad)

{

//list.Items.Clear();

foreach (Item item in Item.Items)

{

ListViewGroup group = new ListViewGroup(item.Group.Name);

list.Groups.Add(group);

list.Items.Add(

new ListViewItem(

item.Title,

group)

);

Console.WriteLine(item.Title + " " + item.Group.Name);

}

}

}

}

Now, the above exact code works in an older program (few months old), but it's not working in a new program. I have no idea why. I have set breakpoints EVERYWHERE and it has proven to be kind of pointless in this case.

One thing I did learn from setting a breakpoint is that even though the stream contains the data expected, the very next second, when it gets added to list, it is NULL. There is nothing in the list. I've run out of ideas, and Google wasn't of much help.

Group.cs:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.Text;

using System.Threading.Tasks;

namespace Notes

{

[DataContract]

public class Group

{

[DataMember]

public string Name { get; set; }

}

}

Item.cs:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.Text;

using System.Threading.Tasks;

namespace Notes

{

[DataContract]

[Serializable]

public class Item : Note

{

[DataMember]

public static List<Item> Items = new List<Item>();

[DataContract]

public enum ItemType

{

Group,

Note

}

[DataMember]

public ItemType Type { get; set; }

[DataMember]

public int Index { get; set; }

}

}

Note.cs:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.Text;

using System.Threading.Tasks;

namespace Notes

{

[DataContract]

public class Note

{

[DataMember]

public string Title { get; set; }

[DataMember]

public string Content { get; set; }

[DataMember]

public Group Group;

[DataContract]

public enum NoteImportance

{

Important,

Neutral,

NotImportant

}

[DataMember]

public NoteImportance Importance { get; set; }

[DataMember]

public bool Protected { get; set; }

}

}

How can I deserialize these objects/read from file and get them into a List or ListView? I've already done this, but for some reason it's not working anymore.

Any help would be appreciated.

网友答案:

When you create a .group file, you serialize a single Item:

    DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(Item));

    // And later
    serializer.WriteObject(stream, item);

But when you deserialize the contents of a .group file, you try to deserialize a List<Item>:

    DataContractJsonSerializer serializer = new DataContractJsonSerializer(typeof(List<Item>));

    // And later
    foreach (Item item in (List<Item>)serializer.ReadObject(stream))
    {
        Item.Items.Add(item);
    }

Those types don't match. But in order to deserialize the data you previously serialized, they need to match - or at least, the deserialized type cannot be a collection if the serialized type was, because collections are serialized as JSON arrays while other classes are serialized as JSON objects (name/value pairs).

Since it looks like each .group file has a single item, and there are many .group files in the directory you are scanning, you probably just want to do

    var serializer = new DataContractJsonSerializer(typeof(Item));

    // And later
    var item = (Item)serializer.ReadObject(stream);
    if (item != null)
        Item.Items.Add(item);
分享给朋友:
您可能感兴趣的文章:
随机阅读: