Я попытался напечатать все вложенные ключи в «items» из файла json (показано ниже), но получил недопустимое исключение приведения в этой строке:

foreach (KeyValuePair<string, JToken> sub in (JObject)obj2["items"])

Я понятия не имею, почему он продолжает показывать эту ошибку.

using Newtonsoft.Json.Linq;
using Newtonsoft.Json;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using UnityEngine;


public class JsonReader : MonoBehaviour
{
    [SerializeField]
    public string filePath;

    [ContextMenu("Load Data")]
    private void LoadData()
    {
        JObject obj2 = JsonConvert.DeserializeObject<JObject>(File.ReadAllText(filePath));
        foreach (KeyValuePair<string, JToken> sub in (JObject)obj2["items"])
        {

            Debug.Log(sub.Key);
        }
    }   
}

Содержимое файла JSON

{
    "items": [
        {
            "id": "143675",
            "item": "Action Figure",
            "name": "Goku",
            "color": "Orange"
        },
        {
            "id": "258943",
            "item": "Water Bottle",
            "name": "Pcares",
            "color": "Silver"
        },
        {
            "id": "326824",
            "item": "White Board",
            "name": "Boardy",
            "color": "White"
        },
        {
            "id": "423168",
            "item": "Monitor",
            "name": "Dell",
            "color": "Black"
        }
    ]
}

Я хочу, чтобы ожидаемый вывод отображал все ключи, например:

id
item
name
color

Любая помощь была бы признательна!

0
shizzlinskillets 2 Май 2019 в 09:42

3 ответа

Лучший ответ

Если вы посмотрите внимательно, значение под ключом items является массивом:

"items": [ // <--- square bracket!
    {
        "id": "143675",
        "item": "Action Figure",
        "name": "Goku",
        "color": "Orange"
    },

Ключи, которые вы хотите получить, находятся в элементах массива. Предполагая, что в массиве всегда будут элементы, вы можете сделать:

foreach (KeyValuePair<string, JToken> sub in (JObject)obj2["items"][0]) 

Обратите внимание на [0] в конце. Это получает первый элемент массива.

4
Sweeper 2 Май 2019 в 06:49

Вы используете KeyValuePair<string, JToken> в foreach

Но учтите, что KeyValuePair используется при десериализации JSON, когда в вашем JSON есть key: value пара, подобная

{
  "ABC" : {
      "X" : "x",
      "Y" : "y",
      "Z" : "z"
  }
}

Выше json ABC является Key в KeyValuePair, а весь объект, связанный с ABC, является Value из ABC ключа.

< Сильный > Но

Ваш json немного отличается от указанного выше, это означает, что у вас есть массив объектов, связанных с ключом items

И вы используете (JObject)obj2["items"], что означает, что вы перебираете массив items, но внутри массива items нет пары ключ / значение, есть только объекты

Пока вам нужно использовать что-то вроде ниже,

foreach (JObject jObject in (JArray)obj2["items"])
{
    Debug.Log(jObject["id"].ToString());
    Debug.Log(jObject["item"].ToString());
    Debug.Log(jObject["name"].ToString());
    Debug.Log(jObject["color"].ToString());
}

Таким образом, вы можете получить все объекты в вашем массиве items

0
er-sho 2 Май 2019 в 07:31

Вы написали foreach (KeyValuePair<string, JToken> sub in (JObject)obj2["items"])

Здесь obj2["items"] имеет тип JArray, а не JObject

invalidCastException потому что вы пытаетесь привести тип объекта JArray к JObject в выражении foreach.

Исходя из того, чего вы хотите достичь в конечном итоге, кажется, что вы написали все правильно, но не добавили [0] в конце (JObject)obj2["items"]

Таким образом, правильное утверждение foreach будет следующим:

foreach (KeyValuePair<string, JToken> sub in (JObject)obj2["items"][0]) // you missed to add this [0] in your code

0
akg179 2 Май 2019 в 08:01