Bir listeyi JSON'a seri hale getirme


182

Şöyle bir nesne modeli var:

public MyObjectInJson
{
   public long ObjectID {get;set;}
   public string ObjectInJson {get;set;}
}

Özellik ObjectInJson, iç içe listeler içeren bir nesnenin zaten serileştirilmiş bir sürümüdür. Şu an için MyObjectInJsonmanuel olarak bu listeyi seri hale getiriyorum :

StringBuilder TheListBuilder = new StringBuilder();

TheListBuilder.Append("[");
int TheCounter = 0;

foreach (MyObjectInJson TheObject in TheList)
{
  TheCounter++;
  TheListBuilder.Append(TheObject.ObjectInJson);

  if (TheCounter != TheList.Count())
  {
    TheListBuilder.Append(",");
  }
}
TheListBuilder.Append("]");

return TheListBuilder.ToString();

Bu tür tehlikeli kodları değiştirip değiştiremeyeceğimi merak ediyorum JavascriptSerializer. Bunu nasıl yaparım?

Teşekkürler.


Not WPF projesinde, sen bir başvuru eklemek gerektiğini System.Web.Extensionskullanımına System.Web.Script.Serialization: stackoverflow.com/a/18746092/1599699 stackoverflow.com/a/19299695/1599699
Andrew

Yanıtlar:


338

Net Core 3.0 veya üstünü kullanıyorsanız;

System.Text.JsonYerleşik ayrıştırıcı uygulamasını kullanma varsayılanıdır .

Örneğin

using System.Text.Json;

var json = JsonSerializer.Serialize(aList);

alternatif olarak, Utf8Json ayrıştırıcı ve Jil gibi diğer daha az ana akım seçenekleri de mevcuttur : Bunlar gerçekten ihtiyacınız varsa üstün performans sunabilir , ancak ilgili paketleri kurmanız gerekir.

Net Core 2.2 veya daha eski bir sürümü kullanarak takılırsa;

İlk tercihiniz JSON Parser olarak Newtonsoft JSON.Net'i kullanmak için varsayılan değerdir.

Örneğin

using Newtonsoft.Json;

var json = JsonConvert.SerializeObject(aList);

önce paketi yüklemeniz gerekebilir.

PM> Install-Package Newtonsoft.Json

Daha fazla ayrıntı için bu bilgilerin kaynağı olan cevaba bakın ve onaylayın .

Sadece referans olarak, bu yıllar önce orijinal cevaptı;

// you need to reference System.Web.Extensions

using System.Web.Script.Serialization;

var jsonSerialiser = new JavaScriptSerializer();
var json = jsonSerialiser.Serialize(aList);

1
ah tamam, AYRICA sadece nesnelerin değil, nesne listelerini de serileştirir. Teşekkürler.
frenchie

döngüsel ilişkiler gibi değil ama bu burada bir sorun değil
Jodrell

13
Bu ad alanının kurnazca System.Web.Extensions içinde sıkışmış olduğunu unutmayın. Bunu referans olarak ekledikten sonra, çözüm mükemmel bir şekilde çalışır!
Sekiz Bit Gurusu

1
Düzenlenmiş cevabınızı görüyorum ve güncellenmiş bir örneğimin olmasını dilerim.
Dylan Brams

1
@ IamNumber5 diğer yanıtta zaten sağlandı. Yine de cevabımı uzattım.
Jodrell

111

Json.NET'i de kullanabilirsiniz. Sadece http://james.newtonking.com/pages/json-net.aspx adresinden indirin. , sıkıştırılmış dosyayı çıkarın ve referans olarak ekleyin.

Ardından listeyi (veya istediğiniz herhangi bir nesneyi) aşağıdakilerle serileştirin:

using Newtonsoft.Json;

string json = JsonConvert.SerializeObject(listTop10);

Güncelleme: NuGet Paket Yöneticisi aracılığıyla projenize de ekleyebilirsiniz (Araçlar -> NuGet Paket Yöneticisi -> Paket Yöneticisi Konsolu):

PM> Install-Package Newtonsoft.Json

Belgeler: Koleksiyonları Serileştirme


12

Yerleşik JSON serileştiricileri ile bunu yapmanın iki yaygın yolu vardır:

  1. JavaScriptSerializer

    var serializer = new JavaScriptSerializer();
    return serializer.Serialize(TheList);
  2. DataContractJsonSerializer

    var serializer = new DataContractJsonSerializer(TheList.GetType());
    using (var stream = new MemoryStream())
    {
        serializer.WriteObject(stream, TheList);
        using (var sr = new StreamReader(stream))
        {
            return sr.ReadToEnd();
        }
    }

    Bu seçeneğin, sınıfınız için bir veri sözleşmesinin tanımlanmasını gerektirdiğini unutmayın:

    [DataContract]
    public class MyObjectInJson
    {
       [DataMember]
       public long ObjectID {get;set;}
       [DataMember]
       public string ObjectInJson {get;set;}
    }

5
public static string JSONSerialize<T>(T obj)
        {
            string retVal = String.Empty;
            using (MemoryStream ms = new MemoryStream())
            {
                DataContractJsonSerializer serializer = new DataContractJsonSerializer(obj.GetType());
                serializer.WriteObject(ms, obj);
                var byteArray = ms.ToArray();
                retVal = Encoding.UTF8.GetString(byteArray, 0, byteArray.Length);
            }
            return retVal;
        }

4

.NET , sürüm 3.5'ten beri System.Runtime.Serialization.Json ad alanı ve DataContractJsonSerializer sınıfı aracılığıyla temel Json serileştirmeyi zaten desteklemektedir . Adından da anlaşılacağı gibi, DataContractJsonSerializer, nihai Json çıktısını oluşturmak için nesnelerinize eklediğiniz veri ek açıklamalarını dikkate alır.

Json'u bir akışa serileştirmek istediğiniz ek açıklamalı veri sınıflarınız varsa, Nasıl Yapılır: JSON Verilerini Diziselleştirin ve Diziselleştirmeyi Kaldırma bölümünde açıklandığı gibi kullanışlı olabilir . Sınırlamalar var, ancak temel ihtiyaçlarınız varsa ve Projenize Yet Another Library'yi eklemek istemiyorsanız yeterince iyi ve hızlı.

Aşağıdaki kod, konsol çıkış akışına bir liste serileştirir. Gördüğünüz gibi Json.NET'ten biraz daha ayrıntılı ve tipte güvenli değil (yani jenerik yok)

        var list = new List<string> {"a", "b", "c", "d"};

        using(var output = Console.OpenStandardOutput())                
        {                
            var writer = new DataContractJsonSerializer(typeof (List<string>));
            writer.WriteObject(output,list);
        }

Öte yandan, Json.NET , Json'u nasıl ürettiğiniz üzerinde çok daha iyi kontrol sağlar. Javascript dostu ad adlarını .NET sınıflarıyla eşleştirmek, tarihleri ​​json'a biçimlendirmek vb. İçin çok kullanışlı olacaktır.

Başka bir seçenek ise , Json, JSV ve CSV için çok hızlı serileştiriciler sağlayan ServicStack ... yığınının bir parçası olan ServiceStack.Text .


0

başka bir gönderiden gelen cevap üzerine .. Json.NET sürüm 12.x ile dinamik erişim kullanarak bir liste oluşturmak için daha genel bir yol buldum

using Newtonsoft.Json;

static class JsonObj
{
    /// <summary>
    /// Deserializes a json file into an object list
    /// Author: Joseph Poirier 2/26/2019
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="fileName"></param>
    /// <returns></returns>
    public static List<T> DeSerializeObject<T>(string fileName)
    {
        List<T> objectOut = new List<T>();

        if (string.IsNullOrEmpty(fileName)) { return objectOut; }

        try
        {
            // reading in full file as text
            string ss = File.ReadAllText(fileName);

            // went with <dynamic> over <T> or <List<T>> to avoid error..
            //  unexpected character at line 1 column 2
            var output = JsonConvert.DeserializeObject<dynamic>(ss);

            foreach (var Record in output)
            {
                foreach (T data in Record)
                {
                    objectOut.Add(data);
                }
            }
        }
        catch (Exception ex)
        {
            //Log exception here
            Console.Write(ex.Message);
        }

        return objectOut;
    }
}

işleme çağrısı

{
        string fname = "../../Names.json"; // <- your json file path

        // for alternate types replace string with custom class below
        List<string> jsonFile = JsonObj.DeSerializeObject<string>(fname);
}

veya bu işleme çağrısı

{
        string fname = "../../Names.json"; // <- your json file path

        // for alternate types replace string with custom class below
        List<string> jsonFile = new List<string>();
        jsonFile.AddRange(JsonObj.DeSerializeObject<string>(fname));
}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.