静态列表<item>()</item>中的项目

时间:2015-02-04 20:14:02

标签: c# reference pass-by-reference

所以我有一个静态项列表,它存储了几个类,在这些类中有变量,如&#34; int ID&#34;,&#34; string name&#34;,&#34; string description& #34;,&#34; int currentAmount&#34;等等

ItemDatabase.cs...

public static List<Item> Items

static void LoadItemData()
{
    Items.Add(new item);
    ...
}

然后我有一个单独的项目列表,其中会添加项目供玩家使用。

Player.cs...

List<Item> playerItems;

然后在其他课程中,我有AddItem(int ID)个方法:

void AddItem(int id)
{
    foreach (Item i in ItemDatabase.Items)
        if (i.ID == id)
            playerItems.Add(i);
}

我目前正在添加将使用相同数据的实体。但是当我修改添加到playerItems的Item时,它会修改ItemDatabase.Items(显然,由于引用)。

我无法将Item类变成结构体,因为我有其他类派生它。 我需要&#34; currentAmount&#34;整数是按值。我有什么方法可以做到这一点吗?

P.S。,我尝试过深度克隆,但这与我的Item类没有很好的搭配。

4 个答案:

答案 0 :(得分:1)

您需要将currentAmount分开。由于该值仅在Player 的上下文中有意义,我会将其从Item类中取出,并使用Dictionary<Item,int>来跟踪库存:

Dictionary<Item, int> inventory = new Dictionary<Item, int>();

void AddItem(int id)
{
    foreach (Item i in ItemDatabase.Items)
        if (i.ID == id)
            playerItems.Add(i, 0); //Or whatever count
}

答案 1 :(得分:1)

显然,如果要在不影响原始对象的情况下更改对象,则需要克隆对象。序列化是进行“深度克隆”的一种方法,但是您发现并非所有类型都可以序列化。

如果您只是修改第一级值类型属性(不更改相关项的值或引用),则可以使用object.MemberwiseClone创建副本(值类型的副本和参考文献)。

答案 2 :(得分:0)

我还不确定你在哪里修改ItemsDatabase.Items(currentAmount作为Entity的属性并没有更多的意义),但是对于库存中的当前金额,我想这对你有所帮助:

Dictionary<Item, int> inventory = new Dictionary<Item, int>();

void AddItem(int id)
{
    foreach (Item i in ItemDatabase.Items)
        if (i.ID == id)
            {
              if(!inventory.Keys.Contains(i)){iventory.Add(i, 0);}
              inventory[i]+=1; //increment the amount of items in inventory.
            }
}

重要的:

Dictionary使用Hash从字典中获取对象,因此,您可能希望在Item类中覆盖该方法:

class Item {
    public string Name;
    public string Description;
    public int currentAmount;

    public override int GetHashCode(){
       return Name.GetHashCode() + Description.GetHashCode();
    }
}

了解更多信息:

答案 3 :(得分:0)

这样做:

void AddItem(int id)
{
    var item = ItemDatabase.Items.FirstOrDefault(x=> x.ID == id);
    if(item!=null){
        playerItems.Add(new Item(){ ID = item.ID, Name = item.Name, etc... })
    }
}