Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
413 views
in Technique[技术] by (71.8m points)

c# - How do I skip default JavaScript array serialization for IEnumerable types in Json.Net?

Some custom types that implement IEnumerable don't necessarily have backing collections. They could be generated dynamically, for example using 'yield' or LINQ. Here is an example:

public class SOJsonExample
{
    public class MyCustomEnumerable : IEnumerable<KeyValuePair<int,float>>
    {
        public List<int> Keys { get; set; }
        public List<float> Values { get; set; }

        public MyCustomEnumerable()
        {
            Keys = new List<int> { 1, 2, 3 };
            Values = new List<float> { 0.1f, 0.2f, 0.3f };
        }

        public IEnumerator<KeyValuePair<int, float>> GetEnumerator()
        {
            var kvps =
                from key in Keys
                from value in Values
                select new KeyValuePair<int, float>(key, value);

            return kvps.GetEnumerator();
        }

        IEnumerator IEnumerable.GetEnumerator()
        {
            return this.GetEnumerator();
        }
    }
}

I have discovered that the default serialization by Json.NET is to enumerate each value and store the values in a JavaScript array (which I don't want). The default deserializer will then fail to deserialize the collection as it can't be populated. In these cases, I'd instead want Json.NET to skip the default JavaScript array serialization, and just store the members of the class.

All I want is my keys and values - is there any shortcut way to do this, or do I have to implement my own custom serializer?

Checked this and this, neither of which are exactly my question. Scanned the documentation as well, but didn't find what I was looking for (perhaps I looked in the wrong place).

(Edit #1 - improved clarity)

(Edit #2 - answered my own question...see below)

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Answered my own question - see the excellent documentation on IEnumerable, Lists, and Arrays:

.NET lists (types that inherit from IEnumerable) and .NET arrays are converted to JSON arrays. Because JSON arrays only support a range of values and not properties, any additional properties and fields declared on .NET collections are not serialized. In situations where a JSON array is not wanted the JsonObjectAttribute can be placed on a .NET type that implements IEnumerable to force the type to be serialized as a JSON object instead.

So, for my example:

[JsonObject]
public class MyCustomEnumerable : IEnumerable<KeyValuePair<int,float>>
{
    ...
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...