我想要的是能够将一个项目的副本与其原始副本匹配。我尝试运行的代码如下所示。我想检查库存中的物品是否与手工系统所需的物品匹配。这两个项目是相同的,唯一的区别是我的库存中的项目(左)是原件的副本,而我的制作系统中的项目是原件(右)。
下面的代码是stringbuilder的一部分。在运行时,它将显示玩家所需的物品数量以及制作工艺所需的物品数量。如果我使用原始项目而不是其副本,则该代码有效,但是由于我获取的是项目副本而不是其原始副本,因此我不知道如何进行此检查。
我尝试匹配它们的名称,但是那根本不起作用,团结抛出了空引用异常。我已经进行了大约6到7个月的编程,但是还不太熟练。我在这些事情上经常陷入困境,如果有人能帮助我,我将不胜感激。
if (Icont.islots[i].item == reci.Materials[0].item)
{
sb0.Length = 0;
Itemslot0(Icont.islots[i].item.amount, reci.Materials[0].amount);
iteminfo[0].text = sb0.ToString();
}
我尝试过的事情是,匹配名称,匹配id,在两侧使用副本,但是所有这些都在我的脸上抛出了null引用异常。如果您考虑一下,这是显而易见的,因为每个副本都有自己的ID,因此它们将不匹配,但是我对于为什么无法使用它们的名称匹配对象感到困惑。
答案 0 :(得分:1)
您的问题出在这一行:if (Icont.islots[i].item == reci.Materials[0].item)
由于您要比较的项目是reference types(我假设它们是“类”),因此您使用默认的==
运算符将进行引用相等性检查(除非您对其进行了重载,似乎您还没有)。
这意味着==
将检查两个项目是否是对内存中同一对象的引用。这就是为什么您看到期望的行为的原因,而当一个仅仅是另一个的克隆时就会看到不期望的行为的原因。
您可以通过多种方式解决此问题;您可以将项目类型更改为value type(Struct
),可以重载==
运算符,可以使用自定义相等比较,然后列表将继续。
我个人要做的是创建一个自定义的相等比较函数,该函数本质上说“如果这些属性相同,则项目1等于项目2”。
一个小例子是:
public static bool IsEqualTo(this Item thisItem, Item otherItem)
{
if (thisItem is null) return otherItem is null;
else if (otherItem is null) return thisItem is null;
return thisItem.property1 == otherItem.property1
&& thisItem.property2 == otherItem.property2
&& thisItem.property3 == otherItem.property3;
}
然后只需更改
if (Icont.islots[i].item == reci.Materials[0].item)
到
if (Icont.islots[i].item.IsEqualTo(reci.Materials[0].item))
此方法使您可以控制如何定义相等性。例如,您可能会说游戏中的每个不同项目都有一些Id
属性,该属性对于该项目类型是唯一的。如果是这种情况,那么您的IsEqualTo()
方法只需要返回两个对象是否具有相同的ID。
编辑:正如@ScottHannen在评论中所说,如果您收到NullReferenceException
,则表示您所引用的项之一实际上并未初始化。确保两个项目上所需的每个对象和属性都已实际初始化。