简体   繁体   English

System.Collections.Generic.KeyNotFoundException:字典中不存在给定的键“Item”

[英]System.Collections.Generic.KeyNotFoundException : The given key 'Item' was not present in the dictionary

I'm trying to implement a basic sprite game in C#.我正在尝试用 C# 实现一个基本的精灵游戏。 I'm testing to see if two dictionaries are equal to each other and I'm having an issue with Containskey() as well as my Equals function in the sprite class.我正在测试两个字典是否彼此相等,并且我在精灵类中的 Containskey() 和 Equals 函数有问题。

public class Sprite
{
    private Point p;
    private uint Horiz;
    private uint Vert;
    private uint Health;
    private uint Shield;
    private Dictionary<Item, int> inv;
    private string[] QuickSlots;

    /* Default constructor
     * set all values to 0
     */
    //string[] empty;
    //string [] mt;
    public Sprite()
    {
        Point newpoint = new Point();
        newpoint.SetX(0);
        newpoint.SetY(0);
        newpoint.SetZ(0);
        p = newpoint;
        Horiz = 0;
        Vert = 0;
        Health = 0;
        Shield = 0;
        inv = null;
        QuickSlots = null;
    }

    public override int GetHashCode()
    {
        return (int)(p.GetX() ^ (p.GetY() << 8) ^ (p.GetZ() << 16) ^
            Horiz ^ (Vert << 9) ^ 
            (Health << 18) ^ (Shield << 25));
    }

    public bool DictionaryEquals(Dictionary<Item, int> inv2)
    {
        foreach(KeyValuePair<Item, int> entry in inv2)
        {
            if(inv.ContainsKey(entry.Key)) //(inv[entry.Key] == inv2[entry.Key]))
            {
                if((inv[entry.Key] == inv2[entry.Key]))
                {
                    continue;
                }
                else{
                    return false;
                }
            }
            else
            {
                return false;
            }
        }
        return true;
    }

    public override bool Equals(Object obj)
    {
        //Check for null and compare run-time types.
            if ((obj == null) || ! this.GetType().Equals(obj.GetType()))
            {
                return false;
            }
            else 
        {
                Sprite s = (Sprite) obj;
            //   this.PrintInventory();
                s.PrintInventory();
            return 
                ((p.Equals(s.p)) &&
                (inv.Equals(s.inv)) &&
                //(QuickSlots == s.QuickSlots) &&
                (Horiz == s.Horiz) &&
                (Vert == s.Vert) &&
                (Health == s.Health) &&
                (Shield == s.Shield));
            }
    }

    public bool HasItem(string item)
    {
        return inv.ContainsKey(StringtoItem(item, this));
    }

    public void TakeItem(string item)
    {
        Console.WriteLine("Does this even work\n");
        if(HasItem(item))
        {
            Console.WriteLine("Does this even work2\n");
            int x = inv[StringtoItem(item, this)] - 1;
            if(x > 0)
            {
                Console.WriteLine("Does this even work3\n");
                inv[StringtoItem(item, this)] = x;
            }
            else
            {
                Console.WriteLine("Does this even work4\n");
                inv.Remove(StringtoItem(item, this));
            }
        }
    }
}

Here, the dictionary.Equals() function works correctly but none of my testSprites match my expected Sprites because when I use an item, it doesn't decrement correctly from the testSprite inventory.在这里,dictionary.Equals() 函数正常工作,但我的 testSprite 没有一个与我预期的 Sprite 匹配,因为当我使用一个项目时,它不会从 testSprite 库存中正确递减。 The takeItem function calls the hasItem function to check if a dictionary/inventory has an item and it always returns false because the containskey function is always returning false even though I know for a fact that the dictionary contains the key when print out the contents of the dictionary to the console. takeItem 函数调用 hasItem 函数来检查字典/库存是否有一个项目,它总是返回 false 因为 containskey 函数总是返回 false 即使我知道字典在打印出内容时包含键的事实字典到控制台。

Below is the Item.cs file.下面是 Item.cs 文件。

public class Item
{
        private string name;
        protected Sprite holder;

        public Item(string n, Sprite h)
        //, int hc, int sc, int ec,
        //      uint mh, uint ms, bool i, uint s, uint md)
        {
                name = n;
                holder = h;
        }

        public string GetItemName()
        {
            return name;
        }
   
        public override int GetHashCode()
    {
        return (int)(name.GetHashCode() ^ (holder.GetPoint().GetX() << 8) ^ (holder.GetPoint().GetY() << 16) ^ 
            (holder.GetPoint().GetZ() << 16) ^
            holder.GetHoriz() ^ (holder.GetVert() << 9) ^ 
            (holder.GetHealth() << 18) ^ (holder.GetShield() << 25));
    }




        public override bool Equals(Object obj)
    {
        //Check for null and compare run-time types.
            if ((obj == null) || ! this.GetType().Equals(obj.GetType()))
            {
                return false;
            }
            else 
        {
                Item i = (Item) obj;
            return 
                ((name == i.name) &&
                (holder.Equals(i.holder)));
            }
    }
}

I suspect that something is wrong with one of the GetHashCode functions but I am not entirely sure how to fix it so any help is appreciated.我怀疑 GetHashCode 函数之一有问题,但我不完全确定如何修复它,因此感谢任何帮助。 Thanks谢谢

First of all, Item class should implement IEqualityComparer<Item> .首先, Item 类应该实现IEqualityComparer<Item> Also, == is used for referential equality (for reference types, like Item which is a class), but seems that what you need here is structural equality - so inv[entry.Key] == inv2[entry.Key] will fail - try inv[entry.Key].Equals(inv2[entry.Key]) after implementing IEqualityComparer.此外, ==用于引用相等(对于引用类型,如 Item 是一个类),但似乎您在这里需要的是结构相等 - 所以inv[entry.Key] == inv2[entry.Key]将失败- 在实现 IEqualityComparer 后尝试inv[entry.Key].Equals(inv2[entry.Key])

Info on IEqualityComparer<T> : https://docs.microsoft.com/en-us/dotnet/api/system.collections.generic.iequalitycomparer-1?view=net-5.0关于IEqualityComparer<T>https : IEqualityComparer<T> = IEqualityComparer<T>

暂无
暂无

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

相关问题 System.Collections.Generic.KeyNotFoundException:给定的键不在字典中 - System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary System.Collections.Generic.KeyNotFoundException:字典中不存在给定键“All” - System.Collections.Generic.KeyNotFoundException: The given key 'All' was not present in the dictionary System.Collections.Generic.KeyNotFoundException:从PUSHSHARP发送推送通知时,字典中不存在给定的键 - System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary while sending Push Notifiaction from PUSHSHARP System.Collections.Generic.KeyNotFoundException: &#39;字典中不存在给定的键。&#39; C# 窗口应用程序 - System.Collections.Generic.KeyNotFoundException: 'The given key was not present in the dictionary.' C# windows application 没有 System.Collections.Generic.KeyNotFoundException 的字典键操作 - Operations over dictionary-key without System.Collections.Generic.KeyNotFoundException System.Collections.Generic.KeyNotFoundException似乎没有原因 - System.Collections.Generic.KeyNotFoundException For Seemingly No Reason Windows Phone中的System.Collections.Generic.KeyNotFoundException - System.Collections.Generic.KeyNotFoundException in Windows Phone Facebook MVC应用程序演示中的System.Collections.Generic.KeyNotFoundException - System.Collections.Generic.KeyNotFoundException on Facebook MVC Application demo "为什么 LINQ Sum() 抛出“System.Collections.Generic.KeyNotFoundException”?" - Why LINQ Sum() throws "System.Collections.Generic.KeyNotFoundException"? 您能解释一下此System.Collections.Generic.KeyNotFoundException吗? - Can you explain this System.Collections.Generic.KeyNotFoundException?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM