如何使用 DataContractJsonSerializer

注意

本文與 DataContractJsonSerializer 有關。 對於涉及序列化和還原序列化 JSON 的大部分案例,我們建議使用 System.Text.Json 命名空間中的 API。

JSON (JavaScript 物件標記法) 是一種有效率的資料編碼格式,可以在用戶端瀏覽器與啟用 AJAX 的 Web 服務之間啟用快速的小量資料交換作業。

本文示範如何將 .NET 型別物件序列化為 JSON 編碼資料,然後將 JSON 格式的資料還原序列化為 .NET 型別的執行個體。 這個範例會使用資料合約來示範使用者定義之 Person 型別的序列化與還原序列化,此外,也會使用 DataContractJsonSerializer

一般來說,當您在啟用 AJAX 的端點上所公開的服務作業中使用資料合約類型時,Windows Communication Foundation (WCF) 會自動處理 JSON 序列化和還原序列化。 不過,在某些情況下,您可能需要直接使用 JSON 資料。

本文是以 DataContractJsonSerializer 範例為基礎。

定義 Person 型別的資料合約

  1. Person 附加到類別,並將 DataContractAttribute 屬性附加到要序列化的成員中,以定義 DataMemberAttribute 的資料合約。 如需資料合約的詳細資訊,請參閱設計服務合約

    [DataContract]
    internal class Person
    {
        [DataMember]
        internal string name;
    
        [DataMember]
        internal int age;
    }
    

若要將型別 Person 的執行個體序列化為 JSON

注意

如果在伺服器的傳出回覆序列化期間或是因為某些原因而發生錯誤,該錯誤可能不會被當成錯誤傳回用戶端。

  1. 建立 Person 型別的執行個體。

    var p = new Person();
    p.name = "John";
    p.age = 42;
    
  2. 使用 DataContractJsonSerializer,將 Person 物件序列化為記憶體資料流。

    var stream1 = new MemoryStream();
    var ser = new DataContractJsonSerializer(typeof(Person));
    
  3. 使用 WriteObject 方法,將 JSON 資料寫入資料流。

    ser.WriteObject(stream1, p);
    
  4. 顯示 JSON 輸出。

    stream1.Position = 0;
    var sr = new StreamReader(stream1);
    Console.Write("JSON form of Person object: ");
    Console.WriteLine(sr.ReadToEnd());
    

若要從 JSON 還原序列化型別 Person 的執行個體

  1. 使用 PersonReadObject 方法,將 JSON 編碼的資料還原序列化為 DataContractJsonSerializer 的新執行個體。

    stream1.Position = 0;
    var p2 = (Person)ser.ReadObject(stream1);
    
  2. 顯示結果。

    Console.WriteLine($"Deserialized back, got name={p2.name}, age={p2.age}");
    

範例

// Create a User object and serialize it to a JSON stream.
public static string WriteFromObject()
{
    // Create User object.
    var user = new User("Bob", 42);

    // Create a stream to serialize the object to.
    var ms = new MemoryStream();

    // Serializer the User object to the stream.
    var ser = new DataContractJsonSerializer(typeof(User));
    ser.WriteObject(ms, user);
    byte[] json = ms.ToArray();
    ms.Close();
    return Encoding.UTF8.GetString(json, 0, json.Length);
}

// Deserialize a JSON stream to a User object.
public static User ReadToObject(string json)
{
    var deserializedUser = new User();
    var ms = new MemoryStream(Encoding.UTF8.GetBytes(json));
    var ser = new DataContractJsonSerializer(deserializedUser.GetType());
    deserializedUser = ser.ReadObject(ms) as User;
    ms.Close();
    return deserializedUser;
}

注意

對於具有多個同名成員的資料合約,JSON 序列化程式會擲回序列化例外狀況,如下列範例程式碼所示。

[DataContract]
public class TestDuplicateDataBase
{
    [DataMember]
    public int field1 = 123;
}

[DataContract]
public class TestDuplicateDataDerived : TestDuplicateDataBase
{
    [DataMember]
    public new int field1 = 999;
}

另請參閱