繁体   English   中英

C#Json.Net:{“无法将类型为'System.Boolean [,]'的对象转换为类型为'System.Collections.Generic.ICollection`1 [System.Boolean]'。”}

[英]C# Json.Net: {“Unable to cast object of type 'System.Boolean[,]' to type 'System.Collections.Generic.ICollection`1[System.Boolean]'.”}

我正在尝试反序列化一个复杂的对象,该对象可以包含相同类的实例(WorldInstance,其中可以包含更多WorldInstances),但是它引发了此异常,我不知道为什么或如何解决它。

我知道这有点含糊,但是我不知道需要什么信息,所以我将发布任何关于我的信息。

编辑1:这是我要序列化的整个类。 http://pastebin.com/QTNH1HZH

我认为它在691行的discoveredTiles上失败了,即使它不应该对该数据做任何事情。

您的问题是,您试图使Json.NET反序列化仅获取数组属性discoveredTiles ,如以下类的简化版本所示:

public class WorldInstance
{
    protected WorldTile[,] m_Tiles;
    protected bool[,] m_Discovered;

    public WorldInstance(WorldTile[,] tiles)
    {
        m_Tiles = tiles;
        m_Discovered = new bool[m_Tiles.GetLength(0), m_Tiles.GetLength(1)];
    }

    public WorldTile[,] tiles
    {
        get
        {
            return m_Tiles;
        }
    }

    public bool[,] discoveredTiles
    {
        get
        {
            return m_Discovered;
        }
    }
}

public class WorldTile
{
}

即使该数组已预分配并且具有与JSON数组相同的长度,当前也无法实现,因为Json.NET会尝试反序列化的项目添加到预分配的数组中,这当然是不可能的。 (请注意,将tiles属性传递给构造函数,并将JSON属性名称与构造函数参数名称匹配,即可反序列化。)

对于一维数组属性,抛出的异常说明了此问题:

System.NotSupportedException: Collection was of a fixed size.
   at System.SZArrayHelper.Add[T](T value)
   at Newtonsoft.Json.Utilities.CollectionWrapper`1.Add(T item) in C:\Development\Releases\Json\Working\Newtonsoft.Json\Working-Signed\Src\Newtonsoft.Json\Utilities\CollectionWrapper.cs:line 76
   at Newtonsoft.Json.Utilities.CollectionWrapper`1.System.Collections.IList.Add(Object value) in C:\Development\Releases\Json\Working\Newtonsoft.Json\Working-Signed\Src\Newtonsoft.Json\Utilities\CollectionWrapper.cs:line 194
   at Newtonsoft.Json.Serialization.JsonSerializerInternalReader.CreateObjectUsingCreatorWithParameters(JsonReader reader, JsonObjectContract contract, JsonProperty containerProperty, ObjectConstructor`1 creator, String id) in C:\Development\Releases\Json\Working\Newtonsoft.Json\Working-Signed\Src\Newtonsoft.Json\Serialization\JsonSerializerInternalReader.cs:line 2030

但是对于2d数组,则抛出照明程度较低的InvalidCastException

您可以通过两种方法解决此问题:

  1. WorldInstance中添加一个受保护的构造函数,该结构包括一个bool[,] discoveredTiles [JsonConstructor]参数,并用[JsonConstructor]进行标记,例如:

     [JsonConstructor] protected WorldInstance(WorldTile[,] tiles, bool[,] discoveredTiles) { if (tiles == null || discoveredTiles == null) throw new ArgumentNullException(); // Ensure the tiles and discoveredTiles arrays have the same sizes if (tiles.GetLength(0) != discoveredTiles.GetLength(0) || tiles.GetLength(1) != discoveredTiles.GetLength(1)) throw new InvalidOperationException("tiles.GetLength(0) != discoveredTiles.GetLength(0) || tiles.GetLength(1) != discoveredTiles.GetLength(1)"); m_Tiles = tiles; m_Discovered = discoveredTiles; } 

    请注意,参数名称discoveredTiles必须与相应的序列化属性名称相同。

  2. discoveredTiles标题添加一个私有或受保护的setter,并用[JsonProperty]标记它:

     [JsonProperty] public bool[,] discoveredTiles { get { return m_Discovered; } protected set { if (value == null) throw new ArgumentNullException(); // Ensure the tiles and discoveredTiles arrays have the same sizes if (tiles != null && tiles.GetLength(0) != value.GetLength(0) || tiles.GetLength(1) != value.GetLength(1)) throw new InvalidOperationException("tiles != null && tiles.GetLength(0) != value.GetLength(0) || tiles.GetLength(1) != value.GetLength(1)"); m_Discovered = value; } } 

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM