C# 将一系列相同的JSON对象映射到字典
我在使用JSON.NET将某个JSON字符串映射到C# 将一系列相同的JSON对象映射到字典,c#,json,json.net,C#,Json,Json.net,我在使用JSON.NET将某个JSON字符串映射到字典时遇到问题 我的JSON字符串如下所示: { "map_waypoint": { "file_id": 157353, "signature": "32633AF8ADEA696A1EF56D3AE32D617B10D3AC57" }, "map_waypoint_contested": { "file_id": 102349, "signature": "5EF051273B40CFAC4AEA6C1F1D0DA612C1B0776
字典
时遇到问题
我的JSON字符串如下所示:
{
"map_waypoint": { "file_id": 157353, "signature": "32633AF8ADEA696A1EF56D3AE32D617B10D3AC57" },
"map_waypoint_contested": { "file_id": 102349, "signature": "5EF051273B40CFAC4AEA6C1F1D0DA612C1B0776C" },
"map_waypoint_hover": { "file_id": 157354, "signature": "95CE3F6B0502232AD90034E4B7CE6E5B0FD3CC5F" }
}
public class FilesResponse2: Dictionary<string, Asset>
{
/// <summary>
/// Initializes a new instance of the <see cref="FilesResponse"/> class.
/// </summary>
public FilesResponse2() {
}
/// <summary>
/// Gets the collection of assets by their name.
/// </summary>
public Dictionary<string, Asset> Files { get { return this; } }
/// <summary>
/// Gets the JSON representation of this instance.
/// </summary>
/// <returns>Returns a JSON <see cref="String"/>.</returns>
public override string ToString() {
return JsonConvert.SerializeObject(this);
}
}
// deserialization:
var result22 = JsonConvert.DeserializeObject<FilesResponse2>(json);
我没有为每个对象创建3个相同的类,而是创建了一个适用于所有对象的类Asset
:
public class Asset
{
/// <summary>
/// Initializes a new instance of the <see cref="Asset"/> class.
/// </summary>
public Asset()
{
}
/// <summary>
/// Initializes a new instance of the <see cref="Asset"/> class.
/// </summary>
/// <param name="fileId">The file ID.</param>
/// <param name="signature">The file signature.</param>
[JsonConstructor]
public Asset(string fileId, string signature)
{
this.FileId = fileId;
this.Signature = signature;
}
/// <summary>
/// Gets the file ID to be used with the render service.
/// </summary>
[JsonProperty("file_id")]
public string FileId { get; private set; }
/// <summary>
/// Gets file signature to be used with the render service.
/// </summary>
[JsonProperty("signature")]
public string Signature { get; private set; }
/// <summary>
/// Gets the JSON representation of this instance.
/// </summary>
/// <returns>Returns a JSON <see cref="String"/>.</returns>
public override string ToString()
{
return JsonConvert.SerializeObject(this);
}
}
问题是,我不太确定如何让JSON.NET知道我的JSON字符串中的数据应该放在字典中
理想情况下,我希望能够做到这一点:
var filesResponse = JsonConvert.DeserializeObject<FilesResponse>(jsonString);
foreach (var file in filesResponse.Files)
{
Console.WriteLine("Name = {0}, ID = {1}", file.Key, file.Value.FileId);
}
var filesResponse=JsonConvert.DeserializeObject(jsonString);
foreach(filesResponse.Files中的var文件)
{
WriteLine(“Name={0},ID={1}”,file.Key,file.Value.FileId);
}
我能以某种方式实现这一点吗?如果你想拥有guid,你需要实现你自己的转换器。我的结局是这样的
public class StringGuidConverter: JsonConverter {
public override bool CanConvert(Type objectType) {
return objectType == typeof(string);
}
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) {
return new Guid((string)reader.Value);
}
public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) {
writer.WriteValue(((Guid)value).ToString("N"));
}
}
public class Asset {
/// <summary>
/// Initializes a new instance of the <see cref="Asset"/> class.
/// </summary>
public Asset() {
}
/// <summary>
/// Initializes a new instance of the <see cref="Asset"/> class.
/// </summary>
/// <param name="fileId">The file ID.</param>
/// <param name="signature">The file signature.</param>
[JsonConstructor]
public Asset(string fileId, Guid signature) {
this.FileId = fileId;
this.Signature = signature;
}
/// <summary>
/// Gets the file ID to be used with the render service.
/// </summary>
[JsonProperty("file_id")]
public string FileId { get; private set; }
/// <summary>
/// Gets file signature to be used with the render service.
/// </summary>
[JsonProperty("signature")]
[JsonConverter(typeof(StringGuidConverter))]
public Guid Signature { get; private set; }
/// <summary>
/// Gets the JSON representation of this instance.
/// </summary>
/// <returns>Returns a JSON <see cref="String"/>.</returns>
public override string ToString() {
return JsonConvert.SerializeObject(this);
}
}
public class FilesResponse {
/// <summary>
/// Initializes a new instance of the <see cref="FilesResponse"/> class.
/// </summary>
public FilesResponse() {
}
/// <summary>
/// Initializes a new instance of the <see cref="FilesResponse"/> class.
/// </summary>
/// <param name="files">A collection of assets by their name.</param>
[JsonConstructor]
public FilesResponse(Dictionary<string, Asset> files) {
this.Files = files;
}
/// <summary>
/// Gets the collection of assets by their name.
/// </summary>
[JsonProperty]
public Dictionary<string, Asset> Files { get; private set; }
/// <summary>
/// Gets the JSON representation of this instance.
/// </summary>
/// <returns>Returns a JSON <see cref="String"/>.</returns>
public override string ToString() {
return JsonConvert.SerializeObject(this);
}
}
class Test {
public static void Run() {
var json = @"{
""map_waypoint"": { ""file_id"": 157353, ""signature"": ""32633AF8ADEA696AE32D617B10D3AC57"" },
""map_waypoint_contested"": { ""file_id"": 102349, ""signature"": ""32633AF8ADEA696AE32D617B10D3AC57"" },
""map_waypoint_hover"": { ""file_id"": 157354, ""signature"": ""32633AF8ADEA696AE32D617B10D3AC57"" }
}";
var result2 = JsonConvert.DeserializeObject<FilesResponse>(json);
var result3 = new FilesResponse(JsonConvert.DeserializeObject<Dictionary<string, Asset>>(json));
}
}
你说得对。但是我真的,真的想让
result2
起作用。谢谢你指出这些签名不是guid。史蒂文·列肯斯:FileResponse有可能从字典继承吗?是的,我知道我可以做到这一点。或者,我可以为每个对象创建一个Asset
类型的属性,并使用[JsonPropertyAttribute]
标记这些属性。但实际上,我更希望所有数据都放在一个文件字典中。你知道吗?如果开发人员希望我使用集合类型,他们应该将JSON设计成一个数组。我将继续为每个对象分别添加一个属性。
public class FilesResponse2: Dictionary<string, Asset>
{
/// <summary>
/// Initializes a new instance of the <see cref="FilesResponse"/> class.
/// </summary>
public FilesResponse2() {
}
/// <summary>
/// Gets the collection of assets by their name.
/// </summary>
public Dictionary<string, Asset> Files { get { return this; } }
/// <summary>
/// Gets the JSON representation of this instance.
/// </summary>
/// <returns>Returns a JSON <see cref="String"/>.</returns>
public override string ToString() {
return JsonConvert.SerializeObject(this);
}
}
// deserialization:
var result22 = JsonConvert.DeserializeObject<FilesResponse2>(json);