在C#中,有效的变量名称不能包含短划线。但是在Json中,所有属性名称都基于字符串,因此在Cson中,被认为是C#变量名称的无效字符可能被认为是有效的。
我的问题是,在尝试反序列化为匿名类型时,JSON.Net如何处理在属性名称中包含Dash或其他无效数据,更重要的是,在匿名类型中如何替换无效字符?抓住它。
如果需要示例数据,我可以提供它,但坦率地说,只需在Json Property名称中添加一个Dash( - ),简而言之就是你的情况。
P.S:我无法改变Json本身,因为它是从API中消耗的。
答案 0 :(得分:2)
您可以使用ContractResolver
来操纵JSON.Net如何将C#属性名称映射到JSON名称。
对于您的示例,此代码执行此操作:
class DashContractResolver : Newtonsoft.Json.Serialization.DefaultContractResolver
{
protected override string ResolvePropertyName(string propertyName)
{
// Count capital letters
int upperCount = propertyName.Skip(1).Count(x => char.IsUpper(x));
// Create character array for new name
char[] newName = new char[propertyName.Length + upperCount];
// Copy over the first character
newName[0] = char.ToLowerInvariant(propertyName[0]);
// Fill the character, and an extra dash for every upper letter
int iChar = 1;
for (int iProperty = 1; iProperty < propertyName.Length; iProperty++)
{
if (char.IsUpper(propertyName[iProperty]))
{
// Insert dash and then lower-cased char
newName[iChar++] = '-';
newName[iChar++] = char.ToLowerInvariant(propertyName[iProperty]);
}
else
newName[iChar++] = propertyName[iProperty];
}
return new string(newName, 0, iChar);
}
}
class Program
{
static void Main(string[] args)
{
string json = @"{""text-example"":""hello""}";
var anonymous = new { textExample = "" };
var obj = JsonConvert.DeserializeAnonymousType(json, anonymous,
new JsonSerializerSettings
{
ContractResolver = new DashContractResolver()
});
}
}
它会将UpperCamelCase
和lowerCamelCase
转换为lower-dash-case
。因此映射到您的JSON输入。
此DeserializeAnonymousType
的重载并非总是可用,并且在Visual Studio 2013发布的版本中不可用。当前(稳定的)NuGet包中存在此重载。< / em>的
答案 1 :(得分:1)
我建议查看Json.Net的Dynamic而不是Anonymous UI,它可以将您的数据反序列化为ExpandoObject,这是一种行为类似于字典的动态类型 - 即类似于JavaScript对象。这将意味着允许的属性名称的范围上升,因为它们成为字典键而不是.Net属性。
有点像:Deserialize a property as an ExpandoObject using JSON.NET