C# JSON 将文件反序列化为对象列表失败,并出现将字符串转换为集合错误

C# JSON deserialize a file into object list fails with convert String to Collection error

我有一个学校的小项目,我们正在处理这里的一些 json 事情。 我可以将对象列表写入 JSON 并且此文件是有效的 JSON 格式。 没有,一旦我加载了完全相同的文件,我确实收到了一个错误,抱怨无法转换。这是消息:

Newtonsoft.Json.JsonSerializationException
  HResult=0x80131500
  Message=Error converting value "[
  {
    "ID": 500455154,
    "Title": "GameOne",
    "MinAge": 14,
    "Price": 12.8,
    "State": "New",
    "Players": 4
  },
  {
    "ID": 860100321,
    "Title": "Gametwo",
    "MinAge": 14,
    "Price": 12.8,
    "State": "New",
    "Players": 4
  },
  {
    "ID": 358239485,
    "Title": "Gamethree",
    "MinAge": 14,
    "Price": 12.8,
    "State": "New",
    "Players": 4
  }
]" to type 'System.Collections.Generic.List`1[Ludothek.Game]'. Path '', line 1, position 513.
  Source=Newtonsoft.Json
  StackTrace:
   at Newtonsoft.Json.Serialization.JsonSerializerInternalReader.EnsureType(JsonReader reader, Object value, CultureInfo culture, JsonContract contract, Type targetType)
   at Newtonsoft.Json.Serialization.JsonSerializerInternalReader.CreateValueInternal(JsonReader reader, Type objectType, JsonContract contract, JsonProperty member, JsonContainerContract containerContract, JsonProperty containerMember, Object existingValue)
   at Newtonsoft.Json.Serialization.JsonSerializerInternalReader.Deserialize(JsonReader reader, Type objectType, Boolean checkAdditionalContent)
   at Newtonsoft.Json.JsonSerializer.DeserializeInternal(JsonReader reader, Type objectType)
   at Newtonsoft.Json.JsonSerializer.Deserialize(JsonReader reader, Type objectType)
   at Ludothek.DATA.loadData_Games() in epos\Ludothek\Ludothek\DATA.cs:line 71
   at Ludothek.Program.Main(String[] args) in \r\Program.cs:line 16

  This exception was originally thrown at this call stack:
    [External Code]

Inner Exception 1:
ArgumentException: Could not cast or convert from System.String to System.Collections.Generic.List`1[Ludothek.Game].

这是我加载此文件并将其推送到现有游戏列表的函数:

public List<Game> loadData_Games()
        {
            var Gl = new List<Game>();
            string[] files = Directory.GetFiles(folder, "games.json");
            foreach (var file in files)

                using (StreamReader sr = new StreamReader(file))
                {
                    using (JsonReader jsr = new JsonTextReader(sr)) {
                        var Serializer = new JsonSerializer();

                        Gl = (List<Game>)Serializer.Deserialize(jsr, typeof(List<Game>));
// above is where it hits the fan...
                    }


                }

        
            return Gl;
        }

当然还有游戏class:

public class Game : AbstGame
    {

        [JsonProperty("ID")]
        public override int ID { get ; }
        [JsonProperty("Title")]
        public override string Title { get ; set ; }
        [JsonProperty("MinAge")]
        public override int MinAge { get ; set ; }
        [JsonProperty("Price")]
        public override double Price { get; set ; }
        [JsonProperty("State")]
        public override string State { get; set ; }
        [JsonProperty("Players")]
        public int Players { get; set; }
        
        public Game(string title, int minAge, double price,string state, int players)
        {
            Random rnd = new Random();
            ID = rnd.Next(1, 999999999);
            Title = title;
            MinAge = minAge;
            Price = price;
            State = state;
            Players = players;

        }

我是这样写的:

        public void backUp_Games(List<Game> games)
        {
            string filename = "games";
               string jsonGames = JsonConvert.SerializeObject(games,Formatting.Indented);
            backUp(filename, jsonGames);


        }
        public void backUp(string fileName ,string json)
        {
            string filename = @"C:\.....\Desktop\JsonTest\"+fileName+".json"; // not the actual path ;)
            File.WriteAllText(filename, JsonConvert.SerializeObject(json,Formatting.Indented));

        }

我真的在互联网上寻找解决这个问题的方法,并且已经尝试了其他几种方法。我无法发现问题。还有其他人看到它并可以给我提示吗?

我在代码中所做的就像生成具有某些属性的游戏列表。 window 关闭后,我会将游戏对象列表推入 json 并保护它,一旦我们打开它,它就会重新加载。 所以它必须从 json.

中获取对象列表

非常感谢!

and this file is a valid JSON format

是的,它是有效的 JSON,但不是您所期望的。你写了一个只有一个 JSON 字符串的文件。

简化示例:

"foo"

这是有效的json。它只是一个字符串。你做同样的事情,但字符串内容看起来像 JSON.

"{\"foo\": \"bar\"}"

这仍然只是一个没有 JSON 对象的字符串。

这就是您收到错误的原因:无法从 System.String 转换或转换为 System.Collections.Generic.List`1[Ludothek.Game].

这就是你要做的...

string jsonGames = JsonConvert.SerializeObject(games,Formatting.Indented);
// string jsonGames is the JSON you want but then you do...
File.WriteAllText(filename, JsonConvert.SerializeObject(json,Formatting.Indented));

因此,您执行 JSON 编码两次,JSON 编码 JSON 字符串将产生如上所述的字符串。

解决方案:只编码一次。