Newtonsoft.Json (Json.NET)使用笔记

Newtonsoft.Json

简单介绍

最常用的 JSON 处理库,功能丰富且经过广泛测试,支持复杂的序列化、反序列化、LINQ to JSON 等功能。它是.NET 项目中处理 JSON 的标准工具之一。

许可证

MIT 许可证(开源、免费,可用于商用)。

功能特点

  1. 支持复杂类型、动态类型和匿名类型。
  2. 支持数据验证、格式化、类型转换等。
  3. 支持高性能的流式 JSON 读取和写入。
  4. 提供与 .NET 类库的良好兼容性。

代码示例

基本类型的序列化和反序列化

cs 复制代码
int number = 100;
string jsonNumber = JsonConvert.SerializeObject(number);
number = JsonConvert.DeserializeObject<int>(jsonNumber);

对象与集合的序列化和反序列化

定义一个简单的类:

cs 复制代码
public class Product
{
    public int ProductID { get; set; }
    public string ProductName { get; set; }
    public decimal Price { get; set; }
}

对象的序列化与反序列化

cs 复制代码
Product product = new Product
{
    ProductID = 1,
    ProductName = "Laptop",
    Price = 999.99m
};

string json = JsonConvert.SerializeObject(product, Formatting.Indented);
product = JsonConvert.DeserializeObject<Product>(json);

集合的序列化和反序列化

cs 复制代码
List<Product> products = new List<Product>
{
    new Product { ProductID = 1, ProductName = "Laptop", Price = 999.99m },
    new Product { ProductID = 2, ProductName = "Smartphone", Price = 499.99m },
    new Product { ProductID = 3, ProductName = "Tablet", Price = 299.99m }
};

string json = JsonConvert.SerializeObject(products, Formatting.Indented);
products = JsonConvert.DeserializeObject<List<Product>>(json);

自定义转换器的使用

自定义日期格式

假设有一个类,其中包含日期类型:

cs 复制代码
public class Event
{
    public string EventName { get; set; }
    public DateTime EventDate { get; set; }
}

默认情况下,日期会序列化为 ISO 8601 格式。
如果想使用自定义格式,例如 yyyy-MM-dd,可以使用 JsonSerializerSettings。

cs 复制代码
Event ev = new Event
{
    EventName = "Conference",
    EventDate = new DateTime(2023, 10, 1)
};

JsonSerializerSettings settings = new JsonSerializerSettings
{
    DateFormatString = "yyyy-MM-dd"
};

string json = JsonConvert.SerializeObject(ev, Formatting.Indented, settings);
ev = JsonConvert.DeserializeObject<Event>(json, settings);

自定义转换器处理特殊类型

假设有一个类,包含 TimeSpan 类型,而默认的序列化可能不满足需求。

cs 复制代码
public class Task
{
    public string TaskName { get; set; }
    public TimeSpan Duration { get; set; }
}

创建自定义转换器:

cs 复制代码
public class TimeSpanConverter : JsonConverter<TimeSpan>
{
    public override void WriteJson(JsonWriter writer, TimeSpan value, JsonSerializer serializer)
    {
        writer.WriteValue(value.ToString());
    }

    public override TimeSpan ReadJson(JsonReader reader, Type objectType, TimeSpan existingValue, bool hasExistingValue, JsonSerializer serializer)
    {
        return TimeSpan.Parse((string)reader.Value);
    }
}

使用自定义转换器进行序列化和反序列化

cs 复制代码
Task task = new Task
{
    TaskName = "Write Code",
    Duration = new TimeSpan(2, 30, 0) // 2 小时 30 分钟
};

JsonSerializerSettings settings = new JsonSerializerSettings();
settings.Converters.Add(new TimeSpanConverter());

string json = JsonConvert.SerializeObject(task, Formatting.Indented, settings);
task = JsonConvert.DeserializeObject<Task>(json, settings);

动态类型和 LINQ to JSON

使用动态类型解析未知结构的 JSON

当处理的 JSON 结构未知或动态变化时,可以使用 dynamic 类型。

示例 JSON:

json 复制代码
{
  "Name": "Alice",
  "Age": 30,
  "Skills": ["C#", "WPF", "JSON"]
}

解析动态 JSON:

cs 复制代码
string json = @"{
  ""Name"": ""Alice"",
  ""Age"": 30,
  ""Skills"": [""C#"", ""WPF"", ""JSON""]
}";

dynamic obj = JsonConvert.DeserializeObject<dynamic>(json);
Console.WriteLine($"Name: {obj.Name}");
Console.WriteLine($"Age: {obj.Age}");
Console.WriteLine("Skills:");
foreach (var skill in obj.Skills)
{
    Console.WriteLine($"- {skill}");
}

使用 JObject 和 JToken

cs 复制代码
using Newtonsoft.Json.Linq;

string json = @"{
  ""Name"": ""Alice"",
  ""Age"": 30,
  ""Skills"": [""C#"", ""WPF"", ""JSON""]
}";

JObject obj = JObject.Parse(json);

// 读取值
string name = (string)obj["Name"];
int age = (int)obj["Age"];
JArray skills = (JArray)obj["Skills"];

// 添加新属性
obj["Country"] = "China";

// 删除属性
obj.Property("Age").Remove();

// 遍历所有属性
foreach (var property in obj.Properties())
{
    Console.WriteLine($"{property.Name}: {property.Value}");
}

// 输出修改后的 JSON
string modifiedJson = obj.ToString();
Console.WriteLine(modifiedJson);

输出:

json 复制代码
Name: Alice
Skills: ["C#","WPF","JSON"]
Country: China
{
  "Name": "Alice",
  "Skills": [
    "C#",
    "WPF",
    "JSON"
  ],
  "Country": "China"
}

忽略属性、更改属性名称、设置全局序列化选项

忽略某些属性

使用 [JsonIgnore] 特性可以在序列化和反序列化时忽略某些属性。

定义一个简单的类:

csharp 复制代码
public class User
{
    public string UserName { get; set; }

    [JsonIgnore]
    public string Password { get; set; }
}

示例:

csharp 复制代码
User user = new User
{
    UserName = "Alice",
    Password = "secret"
};

string json = JsonConvert.SerializeObject(user, Formatting.Indented);
Console.WriteLine(json);

输出的 JSON(Password 被忽略):

json 复制代码
{
  "UserName": "Alice"
}

更改属性名称

使用 [JsonProperty] 特性可以更改序列化时的属性名称。

定义一个简单的类:

csharp 复制代码
public class User
{
    [JsonProperty("user_name")]
    public string UserName { get; set; }

    public string Email { get; set; }
}

示例:

csharp 复制代码
User user = new User
{
    UserName = "Alice",
    Email = "[email protected]"
};

string json = JsonConvert.SerializeObject(user, Formatting.Indented);
Console.WriteLine(json);

输出的 JSON(UserName 被更改为 user_name):

json 复制代码
{
  "user_name": "Alice",
  "Email": "[email protected]"
}

设置全局序列化选项

可以通过 JsonSerializerSettings 设置全局的序列化和反序列化选项。

定义一个简单的类:

csharp 复制代码
public class User
{
    public string UserName { get; set; }

    public string Email { get; set; }
}

示例:忽略空值

csharp 复制代码
User user = new User
{
    UserName = "Alice",
};

JsonSerializerSettings settings = new JsonSerializerSettings
{
    NullValueHandling = NullValueHandling.Ignore
};

string json = JsonConvert.SerializeObject(user, Formatting.Indented, settings);
Console.WriteLine(json);

输出的 JSON(Email 被忽略了):

json 复制代码
{
  "UserName": "Alice"
}
相关推荐
帅云毅17 分钟前
Web3.0的认知补充(去中心化)
笔记·学习·web3·去中心化·区块链
豆豆18 分钟前
day32 学习笔记
图像处理·笔记·opencv·学习·计算机视觉
醉酒的李白、31 分钟前
.NET仓储层在 using 块中创建 SqlSugarClient 的风险
.net·仓储模式设计
nenchoumi311939 分钟前
VLA 论文精读(十六)FP3: A 3D Foundation Policy for Robotic Manipulation
论文阅读·人工智能·笔记·学习·vln
凉、介1 小时前
PCI 总线学习笔记(五)
android·linux·笔记·学习·pcie·pci
鬼面瓷2 小时前
CAPL编程_03
前端·数据库·笔记
帅云毅2 小时前
Web漏洞--XSS之订单系统和Shell箱子
前端·笔记·web安全·php·xss
沉迷...2 小时前
详解.vscode 下的json .vscode文件夹下各个文件的作用
ide·vscode·json
丰锋ff3 小时前
考研英一学习笔记
笔记·学习·考研
Invinciblenuonuo3 小时前
FreeRTOS学习笔记【10】-----任务上下文切换
笔记·学习