如何找出 System.Text.Json 中 JsonValue 的类型

Squ*_*ler 16 c# system.text.json

因此,当我有 JsonNode 时,我可以询问它是 JsonObject 还是 JsonArray 并使用它们。但是当节点是一个实际值时,我如何知道它是字符串、数字还是布尔值?

当然,我可以尝试解析该值,但随后在字符串中传输的数字将变成数字而不是我想避免的字符串。

我将 System.Text.Json 与 .NET 6 一起使用。

can*_*on7 7

源头来看,它看起来就像 aJsonValue只是包裹了 a JsonElement。所以你可以这样做.GetValue<JsonElement>()(通过这个检查),然后检查它的ValueKind属性。

  • [来源](https://source.dot.net/#System.Text.Json/System/Text/Json/Nodes/JsonValueOfT.cs,36) 还显示底层值可能不是“JsonElement”。 (5认同)

小智 7

接受的答案仅适用于特定用例,即相关节点的类型为 JsonValue。

我建议更好的选择是首先测试 JSON 中的基本类型。

someObject["SomeNode"] is JsonArray 
someObject["SomeNode"] is JsonObject
someObject["SomeNode"] is JsonValue
Run Code Online (Sandbox Code Playgroud)

如果对象是 JsonValue 类型,则可以使用 tryGetvalue 直接测试预期值类型

someObject["SomeNode"].AsValue().TryGetValue<someType>(out someType result)
Run Code Online (Sandbox Code Playgroud)

如果该值可解析为请求的类型,则 TryGetValue 返回 true。

如果预期的类型完全未知或可变(呃),您可以使用

someObject["SomeNode"].GetValue<JsonElement>().ValueKind 
Run Code Online (Sandbox Code Playgroud)

诡计。但这仅适用于区分 int 和 string 以及 bool 值。在数组上尝试此操作会出现异常。因此,您首先必须使用上面的“is”样式语法进行测试。


小智 5

以下代码适用于 .NET fiddle 和 .NET 6。

笔记:

  • 如果您JsonValue最终来自 a JsonNode.Parse*(...),那么您JsonValue将包含“JSON 类型”。
  • 如果您是使用隐式转换JsonValue创建的,那么您将包含“CLR 类型”。JsonValue.Create()JsonValue
  • 由于下一点,以下代码返回“JSON 类型”的近似“CLR 类型”。
  • JsonValue.GetValue<T>()JsonValue仅当包含“JSON 类型”时才进行类型转换。
  • JsonValue.GetValue<object>()方便地返回基础值,JsonElement如果它是“JSON 类型”,则该值是 a。
public static class JsonValueExtensions
{
    public static Type GetValueType(this JsonValue jsonValue)
    {
        var value = jsonValue.GetValue<object>();
        if (value is JsonElement element)
        {
            return element.ValueKind switch
            {
                JsonValueKind.False => typeof(bool),
                JsonValueKind.True => typeof(bool),
                JsonValueKind.Number => typeof(double),
                JsonValueKind.String => typeof(string),
                var _ => typeof(JsonElement),
            };
        }
        return value.GetType();
    }
}
Run Code Online (Sandbox Code Playgroud)