c# - 如何在 C# 中将 JSON 转换为自定义对象类并访问属性
问题描述
我对 c# 很陌生,我正在尝试操作来自 api restcountries.eu 的数据。我在确定代码转换数据的确切位置时遇到问题。我想要的结果是通过控制台显示特定国家的货币名称(由 3 位字母代码标识)。
using System;
using System.Net;
using System.Text;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Threading.Tasks;
using System.Collections.Generic;
using System.Linq;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
namespace ApiPractice
{
public class Country
{
//Alpha3code
public string Alpha3Code { get; set; }
//country name
public string Name { get; set; }
//population
public int Population { get; set; }
//public string Languages { get; set; }
//flag
public string Flag { get; set; }
//timezone
public string[] TimeZones { get; set; }
//capital
public string Capital { get; set; }
//currency
public Currency Currencies { get; set; }
////bordering countries
public string[] Borders { get; set; }
}
public partial class Currency
{
[JsonProperty("code")]
public string Code { get; set; }
[JsonProperty("Name")]
public string Name { get; set; }
[JsonProperty("Symbol")]
public string Symbol { get; set; }
}
class Program
{
readonly static HttpClient client = new HttpClient();
static void ShowProduct(Country country)
{
Console.WriteLine(country.Currencies.Name);
}
static string ConvertStringArrayToString(string[] array)
{
// Concatenate all the elements into a StringBuilder.
StringBuilder builder = new StringBuilder();
foreach (string value in array)
{
builder.Append(value);
builder.Append(',');
}
return builder.ToString();
}
static async Task<Country> GetCountryAsync(string path)
{
Country country = null;
HttpResponseMessage response = await client.GetAsync(path);
if (response.IsSuccessStatusCode)
{
country = await response.Content.ReadAsAsync<Country>();
}
return country;
}
static void Main()
{
RunAsync().GetAwaiter().GetResult();
}
static async Task RunAsync()
{
// Update port # in the following line.
client.BaseAddress = new Uri("https://restcountries.eu/rest/v2/alpha/");
client.DefaultRequestHeaders.Accept.Clear();
client.DefaultRequestHeaders.Accept.Add(
new MediaTypeWithQualityHeaderValue("application/json"));
try
{
Console.WriteLine("Please write the alpha numeric code for the country requested");
var alphacode= Console.ReadLine();
// Get the product
var product = await GetCountryAsync(alphacode);
ShowProduct(product);
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
Console.ReadLine();
}
}
}
目前这是我在控制台中收到的错误消息:
请填写所请求国家的字母数字代码
美国
无法将当前 JSON 数组(例如 [1,2,3])反序列化为类型“ApiPractice.Currency”,因为该类型需要 JSON 对象(例如 {"name":"value"})才能正确反序列化。
要修复此错误,请将 JSON 更改为 JSON 对象(例如 {"name":"value"})或将反序列化类型更改为数组或实现集合接口的类型(例如 ICollection、IList),例如可以从 JSON 数组反序列化。JsonArrayAttribute 也可以添加到类型中以强制它从 JSON 数组反序列化。
路径“货币”,第 1 行,位置 581。
JSON:
{
"name": "United States of America",
"topLevelDomain": [
".us"
],
"alpha2Code": "US",
"alpha3Code": "USA",
"callingCodes": [
"1"
],
"capital": "Washington, D.C.",
"altSpellings": [
"US",
"USA",
"United States of America"
],
"region": "Americas",
"subregion": "Northern America",
"population": 323947000,
"latlng": [
38.0,
-97.0
],
"demonym": "American",
"area": 9629091.0,
"gini": 48.0,
"timezones": [
"UTC-12:00",
"UTC-11:00",
"UTC-10:00",
"UTC-09:00",
"UTC-08:00",
"UTC-07:00",
"UTC-06:00",
"UTC-05:00",
"UTC-04:00",
"UTC+10:00",
"UTC+12:00"
],
"borders": [
"CAN",
"MEX"
],
"nativeName": "United States",
"numericCode": "840",
"currencies": [
{
"code": "USD",
"name": "United States dollar",
"symbol": "$"
}
],
"languages": [
{
"iso639_1": "en",
"iso639_2": "eng",
"name": "English",
"nativeName": "English"
}
],
"translations": {
"de": "Vereinigte Staaten von Amerika",
"es": "Estados Unidos",
"fr": "États-Unis",
"ja": "アメリカ合衆国",
"it": "Stati Uniti D'America",
"br": "Estados Unidos",
"pt": "Estados Unidos",
"nl": "Verenigde Staten",
"hr": "Sjedinjene Američke Države",
"fa": "ایالات متحده آمریکا"
},
"flag": "https://restcountries.eu/data/usa.svg",
"regionalBlocs": [
{
"acronym": "NAFTA",
"name": "North American Free Trade Agreement",
"otherAcronyms": [],
"otherNames": [
"Tratado de Libre Comercio de América del Norte",
"Accord de Libre-échange Nord-Américain"
]
}
],
"cioc": "USA"
}
解决方案
无法将当前 JSON 数组(例如 [1,2,3])反序列化为类型“ApiPractice.Currency”,因为该类型需要 JSON 对象(例如 {"name":"value"})才能正确反序列化。要修复此错误,请将 JSON 更改为 JSON 对象(例如 {"name":"value"})或将反序列化类型更改为数组或实现集合接口的类型(例如 ICollection、IList),例如可以从 JSON 数组反序列化。JsonArrayAttribute 也可以添加到类型中以强制它从 JSON 数组反序列化。路径“货币”,第 1 行,位置 581。
该错误意味着您的 JSON 的属性“货币”是一个数组,但在您的 Country 类中,属性 Currencies 的类型是对象 Currency。您必须将属性 Currencies 的类型从 Currency 更改为 Currency 列表。
您的财产代码应为:
public IList<Currency> Currencies { get; set; }
此外,在类的构造函数中初始化列表是一个好习惯。因此,在 Country 类中,您必须实现以下构造函数:
public Country() {
Currencies = new List<Currency>();
}
推荐阅读
- php - VSCode 缩进问题上的 Laravel 刀片
- javascript - 在javascript中禁用chrome密码更改警告
- c++ - 我怎样才能设置这个,所以我不能为cin输入超过四个数字?
- r - 如何对 R 中的组执行逐列 wilcox.test
- python - python + postgresql:如何生成 100 万行 x 1000 列的随机数据集
- next.js - 如何使用 Next-Auth 登录表单与 axios 请求而不是默认表单提交
- c# - C# System.Runtime.Serialization.SerializationException:找不到程序集
- java - 在我的情况下,如何在 android studio 中动态添加选择芯片
- amazon-web-services - 将资源推送到云端时出错
- javascript - 是否可以在javascript中以毫秒为单位获取日期对象