Sign Up

Sign Up to our social questions and Answers Engine to ask questions, answer people’s questions, and connect with other people.

Have an account? Sign In

Have an account? Sign In Now

Sign In

Login to our social questions & Answers Engine to ask questions answer people’s questions & connect with other people.

Sign Up Here

Forgot Password?

Don't have account, Sign Up Here

Forgot Password

Lost your password? Please enter your email address. You will receive a link and will create a new password via email.

Have an account? Sign In Now

You must login to ask a question.

Forgot Password?

Need An Account, Sign Up Here

Please briefly explain why you feel this question should be reported.

Please briefly explain why you feel this answer should be reported.

Please briefly explain why you feel this user should be reported.

Sign InSign Up

The Archive Base

The Archive Base Logo The Archive Base Logo

The Archive Base Navigation

  • SEARCH
  • Home
  • About Us
  • Blog
  • Contact Us
Search
Ask A Question

Mobile menu

Close
Ask a Question
  • Home
  • Add group
  • Groups page
  • Feed
  • User Profile
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Buy Points
  • Users
  • Help
  • Buy Theme
  • SEARCH
Home/ Questions/Q 770767
In Process

The Archive Base Latest Questions

Editorial Team
  • 0
Editorial Team
Asked: May 14, 20262026-05-14T18:33:01+00:00 2026-05-14T18:33:01+00:00

I’m working with the DataContractJsonSerializer in Silverlight 4 and would like to deserialize the

  • 0

I’m working with the DataContractJsonSerializer in Silverlight 4 and would like to deserialize the following JSON:

{
    "collectionname":"Books",
    "collectionitems": [
            ["12345-67890",201,
             "Book One"],
            ["09876-54321",45,
             "Book Two"]
        ]
}

Into classes like the following:

class BookCollection
{
  public string collectionname { get; set; }
  public List<Book> collectionitems { get; set; }
}

class Book
{
  public string Id { get; set; }
  public int NumberOfPages { get; set; }
  public string Title { get; set; }
}

What’s the proper place to extend DataContractJsonSerializer to map the unnamed first array element in “collectionitems” to the Id property of the Book class, the second element to the NumberOfPages property and the final element to Title? I don’t have control over the JSON generation in this instance and would like the solution to work with the Silverlight subset of .NET. It would be great if the solution could perform the reverse for serialization as well.

  • 1 1 Answer
  • 0 Views
  • 0 Followers
  • 0
Share
  • Facebook
  • Report

Leave an answer
Cancel reply

You must login to add an answer.

Forgot Password?

Need An Account, Sign Up Here

1 Answer

  • Voted
  • Oldest
  • Recent
  • Random
  1. Editorial Team
    Editorial Team
    2026-05-14T18:33:01+00:00Added an answer on May 14, 2026 at 6:33 pm

    If this weren’t Silverlight, you could use IDataContractSurrogate to use object[] (what’s actually present in your JSON) instead of Book when serializing/deserializing. Sadly, IDataContractSurrogate (and the overloads of the DataContractJsonSerializer constructor which use it) aren’t available in Silverlight.

    On Silverlight, here’s a hacky but simple workaround. Derive the Book class from a type which imlpements ICollection<object>. Since the type in your serialized JSON is object[], the framework will dutifully serialize it into your ICollection<object>, which in turn you can wrap with your properties.

    The easiest (and hackiest) is just to derive from List<object>. This easy hack has the downside that users can modify the underlying list data and mess up your properties. If you’re the only user of this code, that might be OK. With a little more work, you can roll your own implementation of ICollection and permit only enough methods to run for serialization to work, and throwing exceptions for the rest. I included code samples for both approaches below.

    If the above hacks are too ugly for you, I’m sure there are more graceful ways to handle this. You’d probably want to focus your attention on creating a custom collection type instead of List<Book> for your collectionitems property. This type could contain a field of type List<object[]> (which is the actual type in your JSON) which you might be able to convince the serializer to populate. Then your IList implementation could mine that data into actual Book instances.

    Another line of investigation could try casting.For example could you implement an implicit type conversion between Book and string[] and would serialization be smart enough to use it? I doubt it, but it may be worth a try.

    Anyway, here’s code samples for the derive-from-ICollection hacks noted above. Caveat: I haven’t verified these on Silverlight, but they should be using only Silverlight-accessible types so I think (fingers crossed!) it should work OK.

    Easy, Hackier Sample

    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Runtime.Serialization.Json;
    using System.Runtime.Serialization;
    using System.IO;
    
    [DataContract]
    class BookCollection
    {
        [DataMember(Order=1)]
        public string collectionname { get; set; }
    
        [DataMember(Order = 2)]
        public List<Book> collectionitems { get; set; }
    }
    
    [CollectionDataContract]
    class Book : List<object>
    {
        public string Id { get { return (string)this[0]; } set { this[0] = value; } }
        public int NumberOfPages { get { return (int)this[1]; } set { this[1] = value; } }
        public string Title { get { return (string)this[2]; } set { this[2] = value; } }
    
    }
    
    class Program
    {
        static void Main(string[] args)
        {
            DataContractJsonSerializer ser = new DataContractJsonSerializer(typeof(BookCollection));
            string json = "{"
                        + "\"collectionname\":\"Books\","
                        + "\"collectionitems\": [ "
                                + "[\"12345-67890\",201,\"Book One\"],"
                                + "[\"09876-54321\",45,\"Book Two\"]"
                            + "]"
                        + "}";
    
            using (MemoryStream ms = new MemoryStream(Encoding.Unicode.GetBytes(json)))
            {
                BookCollection obj = ser.ReadObject(ms) as BookCollection;
                using (MemoryStream ms2 = new MemoryStream())
                {
                    ser.WriteObject(ms2, obj);
                    string serializedJson = Encoding.UTF8.GetString(ms2.GetBuffer(), 0,  (int)ms2.Length);
                }
            }
        }
    }
    

    Harder, slightly-less-hacky sample

    Here’s the second sample, showing a manual implementation of ICollection, which prevents users from accessing the collection– it supports calling Add() 3 times (during deserialization) but otherwise doesn’t allow modification via ICollection<T>. The ICollection methods are exposed using explicit interface implementation and there are attributes on those methods to hide them from intellisense, which should further reduce the hack factor. But as you can see this is a lot more code.

    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Runtime.Serialization.Json;
    using System.Runtime.Serialization;
    using System.IO;
    using System.Diagnostics;
    using System.ComponentModel;
    
    [DataContract]
    class BookCollection
    {
        [DataMember(Order=1)]
        public string collectionname { get; set; }
    
        [DataMember(Order = 2)]
        public List<Book> collectionitems { get; set; }
    }
    
    [CollectionDataContract]
    class Book : ICollection<object>
    {
        public string Id { get; set; }
        public int NumberOfPages { get; set; }
        public string Title { get; set; }
    
        // code below here is only used for serialization/deserialization
    
        // keeps track of how many properties have been initialized
        [EditorBrowsable(EditorBrowsableState.Never)]
        private int counter = 0;
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        public void Add(object item)
        {
            switch (++counter)
            {
                case 1:
                    Id = (string)item;
                    break;
                case 2:
                    NumberOfPages = (int)item;
                    break;
                case 3:
                    Title = (string)item;
                    break;
                default:
                    throw new NotSupportedException();
            }
        }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        IEnumerator<object> System.Collections.Generic.IEnumerable<object>.GetEnumerator() 
        {
            return new List<object> { Id, NumberOfPages, Title }.GetEnumerator();
        }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() 
        {
            return new object[] { Id, NumberOfPages, Title }.GetEnumerator();
        }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        int System.Collections.Generic.ICollection<object>.Count 
        { 
            get { return 3; } 
        }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        bool System.Collections.Generic.ICollection<object>.IsReadOnly 
        { get { throw new NotSupportedException(); } }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        void System.Collections.Generic.ICollection<object>.Clear() 
        { throw new NotSupportedException(); }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        bool System.Collections.Generic.ICollection<object>.Contains(object item) 
        { throw new NotSupportedException(); }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        void System.Collections.Generic.ICollection<object>.CopyTo(object[] array, int arrayIndex) 
        { throw new NotSupportedException(); }
    
        [EditorBrowsable(EditorBrowsableState.Never)]
        bool System.Collections.Generic.ICollection<object>.Remove(object item) 
        { throw new NotSupportedException(); }
    }
    
    class Program
    {
        static void Main(string[] args)
        {
            DataContractJsonSerializer ser = new DataContractJsonSerializer(typeof(BookCollection));
            string json = "{"
                        + "\"collectionname\":\"Books\","
                        + "\"collectionitems\": [ "
                                + "[\"12345-67890\",201,\"Book One\"],"
                                + "[\"09876-54321\",45,\"Book Two\"]"
                            + "]"
                        + "}";
    
            using (MemoryStream ms = new MemoryStream(Encoding.Unicode.GetBytes(json)))
            {
                BookCollection obj = ser.ReadObject(ms) as BookCollection;
                using (MemoryStream ms2 = new MemoryStream())
                {
                    ser.WriteObject(ms2, obj);
                    string serializedJson = Encoding.UTF8.GetString(ms2.GetBuffer(), 0,  (int)ms2.Length);
                }
            }
        }
    }
    

    BTW, the first time I read your quesiton I skipped over the important Silverlight requirement. Oops! Anyway, if not using Silverlight, here’s the solution I coded up for that case– it’s much easier and I might as well save it here for any Googlers coming later.

    The (on regular .NET framework, not Silverlight) magic you’re looking for is IDataContractSurrogate. Implement this interface when you want to substitute one type for another type when serializing/deserializing. In your case you wnat to substitute object[] for Book.

    Here’s some code showing how this works:

    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Runtime.Serialization.Json;
    using System.Runtime.Serialization;
    using System.IO;
    using System.Collections.ObjectModel;
    
    [DataContract]
    class BookCollection
    {
        [DataMember(Order=1)]
        public string collectionname { get; set; }
    
        [DataMember(Order = 2)]
        public List<Book> collectionitems { get; set; }
    }
    
    class Book 
    { 
      public string Id { get; set; } 
      public int NumberOfPages { get; set; } 
      public string Title { get; set; } 
    } 
    
    // A type surrogate substitutes object[] for Book when serializing/deserializing.
    class BookTypeSurrogate : IDataContractSurrogate
    {
        public Type GetDataContractType(Type type)
        {
            // "Book" will be serialized as an object array
            // This method is called during serialization, deserialization, and schema export. 
            if (typeof(Book).IsAssignableFrom(type))
            {
                return typeof(object[]);
            }
            return type;
        }
        public object GetObjectToSerialize(object obj, Type targetType)
        {
            // This method is called on serialization.
            if (obj is Book)
            {
                Book book = (Book) obj;
                return new object[] { book.Id, book.NumberOfPages, book.Title };
            }
            return obj;
        }
        public object GetDeserializedObject(object obj, Type targetType)
        {
            // This method is called on deserialization.
            if (obj is object[])
            {
                object[] arr = (object[])obj;
                Book book = new Book { Id = (string)arr[0], NumberOfPages = (int)arr[1], Title = (string)arr[2] };
                return book;
            }
            return obj;
        }
        public Type GetReferencedTypeOnImport(string typeName, string typeNamespace, object customData)
        {
            return null; // not used
        }
        public System.CodeDom.CodeTypeDeclaration ProcessImportedType(System.CodeDom.CodeTypeDeclaration typeDeclaration, System.CodeDom.CodeCompileUnit compileUnit)
        {
            return typeDeclaration; // Not used
        }
        public object GetCustomDataToExport(Type clrType, Type dataContractType)
        {
            return null; // not used
        }
        public object GetCustomDataToExport(System.Reflection.MemberInfo memberInfo, Type dataContractType)
        {
            return null; // not used
        }
        public void GetKnownCustomDataTypes(Collection<Type> customDataTypes)
        {
            return; // not used
        }
    }
    
    
    class Program
    {
        static void Main(string[] args)
        {
            DataContractJsonSerializer ser  =
                new DataContractJsonSerializer(
                    typeof(BookCollection), 
                    new List<Type>(),        /* knownTypes */
                    int.MaxValue,            /* maxItemsInObjectGraph */ 
                    false,                   /* ignoreExtensionDataObject */
                    new BookTypeSurrogate(),  /* dataContractSurrogate */
                    false                    /* alwaysEmitTypeInformation */
                    );
            string json = "{"
                        + "\"collectionname\":\"Books\","
                        + "\"collectionitems\": [ "
                                + "[\"12345-67890\",201,\"Book One\"],"
                                + "[\"09876-54321\",45,\"Book Two\"]"
                            + "]"
                        + "}";
    
            using (MemoryStream ms = new MemoryStream(Encoding.Unicode.GetBytes(json)))
            {
                BookCollection obj = ser.ReadObject(ms) as BookCollection;
                using (MemoryStream ms2 = new MemoryStream())
                {
                    ser.WriteObject(ms2, obj);
                    string serializedJson = Encoding.UTF8.GetString(ms2.GetBuffer(), 0,  (int)ms2.Length);
                }
            }
        }
    }
    
    • 0
    • Reply
    • Share
      Share
      • Share on Facebook
      • Share on Twitter
      • Share on LinkedIn
      • Share on WhatsApp
      • Report

Sidebar

Related Questions

I'm parsing an RSS feed that has an &#8217; in it. SimpleXML turns this
I have some data like this: 1 2 3 4 5 9 2 6
I am trying to loop through a bunch of documents I have to put
I'm making a simple page using Google Maps API 3. My first. One marker
I have a bunch of posts stored in text files formatted in yaml/textile (from
We're building an app, our first using Rails 3, and we're having to build
I have this code: - (void)parser:(NSXMLParser *)parser foundCDATA:(NSData *)CDATABlock { NSString *someString = [[NSString

Explore

  • Home
  • Add group
  • Groups page
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Users
  • Help
  • SEARCH

Footer

© 2021 The Archive Base. All Rights Reserved
With Love by The Archive Base

Insert/edit link

Enter the destination URL

Or link to existing content

    No search term specified. Showing recent items. Search or use up and down arrow keys to select an item.